Merge "Maintain internal consistency for TimePickerClockDelegate hour" into nyc-dev
diff --git a/api/current.txt b/api/current.txt
index be9193e..5e4b2d4 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -20728,20 +20728,20 @@
     field public static final int VP8Level_Version2 = 4; // 0x4
     field public static final int VP8Level_Version3 = 8; // 0x8
     field public static final int VP8ProfileMain = 1; // 0x1
-    field public static final int VP9Level1 = 0; // 0x0
-    field public static final int VP9Level11 = 1; // 0x1
-    field public static final int VP9Level2 = 2; // 0x2
-    field public static final int VP9Level21 = 4; // 0x4
-    field public static final int VP9Level3 = 8; // 0x8
-    field public static final int VP9Level31 = 16; // 0x10
-    field public static final int VP9Level4 = 32; // 0x20
-    field public static final int VP9Level41 = 64; // 0x40
-    field public static final int VP9Level5 = 128; // 0x80
-    field public static final int VP9Level51 = 256; // 0x100
-    field public static final int VP9Level52 = 512; // 0x200
-    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 VP9Level1 = 1; // 0x1
+    field public static final int VP9Level11 = 2; // 0x2
+    field public static final int VP9Level2 = 4; // 0x4
+    field public static final int VP9Level21 = 8; // 0x8
+    field public static final int VP9Level3 = 16; // 0x10
+    field public static final int VP9Level31 = 32; // 0x20
+    field public static final int VP9Level4 = 64; // 0x40
+    field public static final int VP9Level41 = 128; // 0x80
+    field public static final int VP9Level5 = 256; // 0x100
+    field public static final int VP9Level51 = 512; // 0x200
+    field public static final int VP9Level52 = 1024; // 0x400
+    field public static final int VP9Level6 = 2048; // 0x800
+    field public static final int VP9Level61 = 4096; // 0x1000
+    field public static final int VP9Level62 = 8192; // 0x2000
     field public static final int VP9Profile0 = 1; // 0x1
     field public static final int VP9Profile1 = 2; // 0x2
     field public static final int VP9Profile2 = 4; // 0x4
diff --git a/api/system-current.txt b/api/system-current.txt
index b787d86..bde3a8c 100644
--- a/api/system-current.txt
+++ b/api/system-current.txt
@@ -22248,20 +22248,20 @@
     field public static final int VP8Level_Version2 = 4; // 0x4
     field public static final int VP8Level_Version3 = 8; // 0x8
     field public static final int VP8ProfileMain = 1; // 0x1
-    field public static final int VP9Level1 = 0; // 0x0
-    field public static final int VP9Level11 = 1; // 0x1
-    field public static final int VP9Level2 = 2; // 0x2
-    field public static final int VP9Level21 = 4; // 0x4
-    field public static final int VP9Level3 = 8; // 0x8
-    field public static final int VP9Level31 = 16; // 0x10
-    field public static final int VP9Level4 = 32; // 0x20
-    field public static final int VP9Level41 = 64; // 0x40
-    field public static final int VP9Level5 = 128; // 0x80
-    field public static final int VP9Level51 = 256; // 0x100
-    field public static final int VP9Level52 = 512; // 0x200
-    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 VP9Level1 = 1; // 0x1
+    field public static final int VP9Level11 = 2; // 0x2
+    field public static final int VP9Level2 = 4; // 0x4
+    field public static final int VP9Level21 = 8; // 0x8
+    field public static final int VP9Level3 = 16; // 0x10
+    field public static final int VP9Level31 = 32; // 0x20
+    field public static final int VP9Level4 = 64; // 0x40
+    field public static final int VP9Level41 = 128; // 0x80
+    field public static final int VP9Level5 = 256; // 0x100
+    field public static final int VP9Level51 = 512; // 0x200
+    field public static final int VP9Level52 = 1024; // 0x400
+    field public static final int VP9Level6 = 2048; // 0x800
+    field public static final int VP9Level61 = 4096; // 0x1000
+    field public static final int VP9Level62 = 8192; // 0x2000
     field public static final int VP9Profile0 = 1; // 0x1
     field public static final int VP9Profile1 = 2; // 0x2
     field public static final int VP9Profile2 = 4; // 0x4
diff --git a/api/test-current.txt b/api/test-current.txt
index 4a8d5f6..9141506 100644
--- a/api/test-current.txt
+++ b/api/test-current.txt
@@ -20796,20 +20796,20 @@
     field public static final int VP8Level_Version2 = 4; // 0x4
     field public static final int VP8Level_Version3 = 8; // 0x8
     field public static final int VP8ProfileMain = 1; // 0x1
-    field public static final int VP9Level1 = 0; // 0x0
-    field public static final int VP9Level11 = 1; // 0x1
-    field public static final int VP9Level2 = 2; // 0x2
-    field public static final int VP9Level21 = 4; // 0x4
-    field public static final int VP9Level3 = 8; // 0x8
-    field public static final int VP9Level31 = 16; // 0x10
-    field public static final int VP9Level4 = 32; // 0x20
-    field public static final int VP9Level41 = 64; // 0x40
-    field public static final int VP9Level5 = 128; // 0x80
-    field public static final int VP9Level51 = 256; // 0x100
-    field public static final int VP9Level52 = 512; // 0x200
-    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 VP9Level1 = 1; // 0x1
+    field public static final int VP9Level11 = 2; // 0x2
+    field public static final int VP9Level2 = 4; // 0x4
+    field public static final int VP9Level21 = 8; // 0x8
+    field public static final int VP9Level3 = 16; // 0x10
+    field public static final int VP9Level31 = 32; // 0x20
+    field public static final int VP9Level4 = 64; // 0x40
+    field public static final int VP9Level41 = 128; // 0x80
+    field public static final int VP9Level5 = 256; // 0x100
+    field public static final int VP9Level51 = 512; // 0x200
+    field public static final int VP9Level52 = 1024; // 0x400
+    field public static final int VP9Level6 = 2048; // 0x800
+    field public static final int VP9Level61 = 4096; // 0x1000
+    field public static final int VP9Level62 = 8192; // 0x2000
     field public static final int VP9Profile0 = 1; // 0x1
     field public static final int VP9Profile1 = 2; // 0x2
     field public static final int VP9Profile2 = 4; // 0x4
diff --git a/core/java/android/animation/ObjectAnimator.java b/core/java/android/animation/ObjectAnimator.java
index 542ecf4..1d10860 100644
--- a/core/java/android/animation/ObjectAnimator.java
+++ b/core/java/android/animation/ObjectAnimator.java
@@ -585,6 +585,11 @@
      * along the way, and an ending value (these values will be distributed evenly across
      * the duration of the animation).
      *
+     * <p><strong>Note:</strong> The values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the animator. If the objects will be mutated externally after
+     * this method is called, callers should pass a copy of those objects instead.
+     *
      * @param target The object whose property is to be animated. This object should
      * have a public method on it called <code>setName()</code>, where <code>name</code> is
      * the value of the <code>propertyName</code> parameter.
@@ -635,6 +640,11 @@
      * along the way, and an ending value (these values will be distributed evenly across
      * the duration of the animation).
      *
+     * <p><strong>Note:</strong> The values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the animator. If the objects will be mutated externally after
+     * this method is called, callers should pass a copy of those objects instead.
+     *
      * @param target The object whose property is to be animated.
      * @param property The property being animated.
      * @param evaluator A TypeEvaluator that will be called on each animation frame to
@@ -663,6 +673,11 @@
      * supplied, the <code>TypeConverter</code> must be a
      * {@link android.animation.BidirectionalTypeConverter} to retrieve the current value.
      *
+     * <p><strong>Note:</strong> The values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the animator. If the objects will be mutated externally after
+     * this method is called, callers should pass a copy of those objects instead.
+     *
      * @param target The object whose property is to be animated.
      * @param property The property being animated.
      * @param converter Converts the animated object to the Property type.
diff --git a/core/java/android/animation/PropertyValuesHolder.java b/core/java/android/animation/PropertyValuesHolder.java
index ffea6f5..224823e 100644
--- a/core/java/android/animation/PropertyValuesHolder.java
+++ b/core/java/android/animation/PropertyValuesHolder.java
@@ -388,6 +388,11 @@
      * set of Object values. This variant also takes a TypeEvaluator because the system
      * cannot automatically interpolate between objects of unknown type.
      *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the PropertyValuesHolder. If the objects will be mutated externally
+     * after this method is called, callers should pass a copy of those objects instead.
+     *
      * @param propertyName The name of the property being animated.
      * @param evaluator A TypeEvaluator that will be called on each animation frame to
      * provide the necessary interpolation between the Object values to derive the animated
@@ -433,6 +438,11 @@
      * set of Object values. This variant also takes a TypeEvaluator because the system
      * cannot automatically interpolate between objects of unknown type.
      *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the PropertyValuesHolder. If the objects will be mutated externally
+     * after this method is called, callers should pass a copy of those objects instead.
+     *
      * @param property The property being animated. Should not be null.
      * @param evaluator A TypeEvaluator that will be called on each animation frame to
      * provide the necessary interpolation between the Object values to derive the animated
@@ -458,6 +468,11 @@
      * must be a {@link android.animation.BidirectionalTypeConverter} to retrieve the current
      * value.
      *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the PropertyValuesHolder. If the objects will be mutated externally
+     * after this method is called, callers should pass a copy of those objects instead.
+     *
      * @param property The property being animated. Should not be null.
      * @param converter Converts the animated object to the Property type.
      * @param evaluator A TypeEvaluator that will be called on each animation frame to
@@ -636,7 +651,12 @@
      * {@link ObjectAnimator}, and with a getter function
      * derived automatically from <code>propertyName</code>, since otherwise PropertyValuesHolder has
      * no way of determining what the value should be.
-     * 
+     *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the PropertyValuesHolder. If the objects will be mutated externally
+     * after this method is called, callers should pass a copy of those objects instead.
+     *
      * @param values One or more values that the animation will animate between.
      */
     public void setObjectValues(Object... values) {
diff --git a/core/java/android/animation/ValueAnimator.java b/core/java/android/animation/ValueAnimator.java
index 31035a7..0a9b5de 100644
--- a/core/java/android/animation/ValueAnimator.java
+++ b/core/java/android/animation/ValueAnimator.java
@@ -353,6 +353,11 @@
      * from the target object and property being animated). Therefore, there should typically
      * be two or more values.
      *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the animator. If the objects will be mutated externally after
+     * this method is called, callers should pass a copy of those objects instead.
+     *
      * <p>Since ValueAnimator does not know how to animate between arbitrary Objects, this
      * factory method also takes a TypeEvaluator object that the ValueAnimator will use
      * to perform that interpolation.
@@ -434,6 +439,11 @@
      * from the target object and property being animated). Therefore, there should typically
      * be two or more values.
      *
+     * <p><strong>Note:</strong> The Object values are stored as references to the original
+     * objects, which means that changes to those objects after this method is called will
+     * affect the values on the animator. If the objects will be mutated externally after
+     * this method is called, callers should pass a copy of those objects instead.
+     *
      * <p>If there are already multiple sets of values defined for this ValueAnimator via more
      * than one PropertyValuesHolder object, this method will set the values for the first
      * of those objects.</p>
diff --git a/core/java/android/app/ActivityManager.java b/core/java/android/app/ActivityManager.java
index d440017..ff8cf66 100644
--- a/core/java/android/app/ActivityManager.java
+++ b/core/java/android/app/ActivityManager.java
@@ -3430,6 +3430,8 @@
     public static final int FLAG_AND_LOCKED = 1 << 1;
     /** {@hide} */
     public static final int FLAG_AND_UNLOCKED = 1 << 2;
+    /** {@hide} */
+    public static final int FLAG_AND_UNLOCKING_OR_UNLOCKED = 1 << 3;
 
     /**
      * Return whether the given user is actively running.  This means that
@@ -3449,26 +3451,6 @@
     }
 
     /** {@hide} */
-    public boolean isUserRunningAndLocked(int userId) {
-        try {
-            return ActivityManagerNative.getDefault().isUserRunning(userId,
-                    ActivityManager.FLAG_AND_LOCKED);
-        } catch (RemoteException e) {
-            throw e.rethrowFromSystemServer();
-        }
-    }
-
-    /** {@hide} */
-    public boolean isUserRunningAndUnlocked(int userId) {
-        try {
-            return ActivityManagerNative.getDefault().isUserRunning(userId,
-                    ActivityManager.FLAG_AND_UNLOCKED);
-        } catch (RemoteException e) {
-            throw e.rethrowFromSystemServer();
-        }
-    }
-
-    /** {@hide} */
     public boolean isVrModePackageEnabled(ComponentName component) {
         try {
             return ActivityManagerNative.getDefault().isVrModePackageEnabled(component);
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index f7c0b4c..6d805ed 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -4617,16 +4617,7 @@
             // onConfigurationChanged
             int diff = activity.mCurrentConfig.diff(newConfig);
             if (diff != 0) {
-                // If this activity doesn't handle any of the config changes then don't bother
-                // calling onConfigurationChanged as we're going to destroy it.
-                // Except in the case where the configuration changed on the activity manager side,
-                // but wasn't big enough to cause a resource change so the activity wasn't destroyed.
-                // In this case we still want to change the configuration of the activity but not
-                // report it to the app.
-                if ((~activity.mActivityInfo.getRealConfigChanged() & diff) == 0
-                        || !reportToActivity) {
-                    shouldChangeConfig = true;
-                }
+                shouldChangeConfig = true;
             }
         }
 
diff --git a/core/java/android/os/FileUtils.java b/core/java/android/os/FileUtils.java
index 7d74a12..fa32848 100644
--- a/core/java/android/os/FileUtils.java
+++ b/core/java/android/os/FileUtils.java
@@ -72,8 +72,13 @@
     public static final int S_IWOTH = 00002;
     public static final int S_IXOTH = 00001;
 
-    /** Regular expression for safe filenames: no spaces or metacharacters */
-    private static final Pattern SAFE_FILENAME_PATTERN = Pattern.compile("[\\w%+,./=_-]+");
+    /** Regular expression for safe filenames: no spaces or metacharacters.
+      *
+      * Use a preload holder so that FileUtils can be compile-time initialized.
+      */
+    private static class NoImagePreloadHolder {
+        public static final Pattern SAFE_FILENAME_PATTERN = Pattern.compile("[\\w%+,./=_-]+");
+    }
 
     private static final File[] EMPTY = new File[0];
 
@@ -243,7 +248,7 @@
         // Note, we check whether it matches what's known to be safe,
         // rather than what's known to be unsafe.  Non-ASCII, control
         // characters, etc. are all unsafe by default.
-        return SAFE_FILENAME_PATTERN.matcher(file.getPath()).matches();
+        return NoImagePreloadHolder.SAFE_FILENAME_PATTERN.matcher(file.getPath()).matches();
     }
 
     /**
diff --git a/core/java/android/os/UserManager.java b/core/java/android/os/UserManager.java
index dd53cbb..d55201f 100644
--- a/core/java/android/os/UserManager.java
+++ b/core/java/android/os/UserManager.java
@@ -36,7 +36,6 @@
 import android.graphics.BitmapFactory;
 import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
-import android.os.storage.StorageManager;
 import android.provider.Settings;
 import android.telephony.TelephonyManager;
 import android.view.WindowManager.LayoutParams;
@@ -984,10 +983,27 @@
 
     /** {@hide} */
     public boolean isUserUnlocked(@UserIdInt int userId) {
-        // TODO: eventually pivot this back to look at ActivityManager state,
-        // but there is race where we can start a non-encryption-aware launcher
-        // before that lifecycle has entered the running unlocked state.
-        return mContext.getSystemService(StorageManager.class).isUserKeyUnlocked(userId);
+        try {
+            return ActivityManagerNative.getDefault().isUserRunning(userId,
+                    ActivityManager.FLAG_AND_UNLOCKED);
+        } catch (RemoteException re) {
+            throw re.rethrowFromSystemServer();
+        }
+    }
+
+    /** {@hide} */
+    public boolean isUserUnlockingOrUnlocked(UserHandle user) {
+        return isUserUnlockingOrUnlocked(user.getIdentifier());
+    }
+
+    /** {@hide} */
+    public boolean isUserUnlockingOrUnlocked(@UserIdInt int userId) {
+        try {
+            return ActivityManagerNative.getDefault().isUserRunning(userId,
+                    ActivityManager.FLAG_AND_UNLOCKING_OR_UNLOCKED);
+        } catch (RemoteException re) {
+            throw re.rethrowFromSystemServer();
+        }
     }
 
     /**
diff --git a/core/java/android/os/storage/StorageManager.java b/core/java/android/os/storage/StorageManager.java
index f68e227..fbf7b26 100644
--- a/core/java/android/os/storage/StorageManager.java
+++ b/core/java/android/os/storage/StorageManager.java
@@ -25,6 +25,7 @@
 import android.content.Context;
 import android.content.pm.IPackageMoveObserver;
 import android.content.pm.PackageManager;
+import android.os.Binder;
 import android.os.Environment;
 import android.os.FileUtils;
 import android.os.Handler;
@@ -1062,11 +1063,20 @@
     }
 
     /** {@hide} */
-    public boolean isUserKeyUnlocked(int userId) {
+    public static boolean isUserKeyUnlocked(int userId) {
+        final IMountService mount = IMountService.Stub
+                .asInterface(ServiceManager.getService("mount"));
+        if (mount == null) {
+            Slog.w(TAG, "Early during boot, assuming locked");
+            return false;
+        }
+        final long token = Binder.clearCallingIdentity();
         try {
-            return mMountService.isUserKeyUnlocked(userId);
+            return mount.isUserKeyUnlocked(userId);
         } catch (RemoteException e) {
-            throw e.rethrowFromSystemServer();
+            throw e.rethrowAsRuntimeException();
+        } finally {
+            Binder.restoreCallingIdentity(token);
         }
     }
 
diff --git a/core/java/android/provider/CallLog.java b/core/java/android/provider/CallLog.java
index 8a0759f..893eb37 100644
--- a/core/java/android/provider/CallLog.java
+++ b/core/java/android/provider/CallLog.java
@@ -824,6 +824,8 @@
                 UserHandle user, ContentValues values) {
             final ContentResolver resolver = context.getContentResolver();
 
+            // Since we're doing this operation on behalf of an app, we only
+            // want to use the actual "unlocked" state.
             final Uri uri = ContentProvider.maybeAddUserId(
                     userManager.isUserUnlocked(user) ? CONTENT_URI : SHADOW_CONTENT_URI,
                     user.getIdentifier());
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index b1bf355..d98e217 100755
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -6869,14 +6869,6 @@
                "hdmi_control_auto_device_off_enabled";
 
        /**
-        * Whether to use the DHCP client from Lollipop and earlier instead of the newer Android DHCP
-        * client.
-        * (0 = false, 1 = true)
-        * @hide
-        */
-       public static final String LEGACY_DHCP_CLIENT = "legacy_dhcp_client";
-
-       /**
         * Whether TV will switch to MHL port when a mobile device is plugged in.
         * (0 = false, 1 = true)
         * @hide
diff --git a/core/java/android/view/DisplayInfo.java b/core/java/android/view/DisplayInfo.java
index 27fe687c..8aeeffd 100644
--- a/core/java/android/view/DisplayInfo.java
+++ b/core/java/android/view/DisplayInfo.java
@@ -380,7 +380,7 @@
         for (int i = 0; i < nColorTransforms; i++) {
             supportedColorTransforms[i] = Display.ColorTransform.CREATOR.createFromParcel(source);
         }
-        hdrCapabilities = Display.HdrCapabilities.CREATOR.createFromParcel(source);
+        hdrCapabilities = source.readParcelable(null);
         logicalDensityDpi = source.readInt();
         physicalXDpi = source.readFloat();
         physicalYDpi = source.readFloat();
@@ -424,7 +424,7 @@
         for (int i = 0; i < supportedColorTransforms.length; i++) {
             supportedColorTransforms[i].writeToParcel(dest, flags);
         }
-        hdrCapabilities.writeToParcel(dest, flags);
+        dest.writeParcelable(hdrCapabilities, flags);
         dest.writeInt(logicalDensityDpi);
         dest.writeFloat(physicalXDpi);
         dest.writeFloat(physicalYDpi);
diff --git a/core/java/android/webkit/WebChromeClient.java b/core/java/android/webkit/WebChromeClient.java
index 4737e9b..2d3b6ab 100644
--- a/core/java/android/webkit/WebChromeClient.java
+++ b/core/java/android/webkit/WebChromeClient.java
@@ -284,6 +284,13 @@
      * currently set for that origin. The host application should invoke the
      * specified callback with the desired permission state. See
      * {@link GeolocationPermissions} for details.
+     *
+     * <p>Note that for applications targeting Android N and later SDKs
+     * (API level > {@link android.os.Build.VERSION_CODES#M})
+     * this method is only called for requests originating from secure
+     * origins such as https. On non-secure origins geolocation requests
+     * are automatically denied.</p>
+     *
      * @param origin The origin of the web content attempting to use the
      *               Geolocation API.
      * @param callback The callback to use to set the permission state for the
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index ada7731..f54edf1 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -255,6 +255,16 @@
  * is loading.
  * </p>
  *
+ * <h3>HTML5 Geolocation API support</h3>
+ *
+ * <p>For applications targeting Android N and later releases
+ * (API level > {@link android.os.Build.VERSION_CODES#M}) the geolocation api is only supported on
+ * secure origins such as https. For such applications requests to geolocation api on non-secure
+ * origins are automatically denied without invoking the corresponding
+ * {@link WebChromeClient#onGeolocationPermissionsShowPrompt(String, GeolocationPermissions.Callback)}
+ * method.
+ * </p>
+ *
  * <h3>Layout size</h3>
  * <p>
  * It is recommended to set the WebView layout height to a fixed value or to
diff --git a/core/java/com/android/internal/content/PackageMonitor.java b/core/java/com/android/internal/content/PackageMonitor.java
index 7bd64e5..c6b6a7fb 100644
--- a/core/java/com/android/internal/content/PackageMonitor.java
+++ b/core/java/com/android/internal/content/PackageMonitor.java
@@ -45,6 +45,7 @@
         sPackageFilt.addAction(Intent.ACTION_PACKAGE_CHANGED);
         sPackageFilt.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART);
         sPackageFilt.addAction(Intent.ACTION_PACKAGE_RESTARTED);
+        sPackageFilt.addAction(Intent.ACTION_PACKAGE_DATA_CLEARED);
         sPackageFilt.addDataScheme("package");
         sNonDataFilt.addAction(Intent.ACTION_UID_REMOVED);
         sNonDataFilt.addAction(Intent.ACTION_USER_STOPPED);
@@ -275,6 +276,9 @@
     public void onFinishPackageChanges() {
     }
 
+    public void onPackageDataCleared(String packageName, int uid) {
+    }
+
     public int getChangingUserId() {
         return mChangeUserId;
     }
@@ -365,6 +369,12 @@
                 }
                 onPackageModified(pkg);
             }
+        } else if (Intent.ACTION_PACKAGE_DATA_CLEARED.equals(action)) {
+            String pkg = getPackageName(intent);
+            int uid = intent.getIntExtra(Intent.EXTRA_UID, 0);
+            if (pkg != null) {
+                onPackageDataCleared(pkg, uid);
+            }
         } else if (Intent.ACTION_QUERY_PACKAGE_RESTART.equals(action)) {
             mDisappearingPackages = intent.getStringArrayExtra(Intent.EXTRA_PACKAGES);
             mChangeType = PACKAGE_TEMPORARY_CHANGE;
diff --git a/core/java/com/android/internal/policy/DecorView.java b/core/java/com/android/internal/policy/DecorView.java
index 645ffda..68a1378 100644
--- a/core/java/com/android/internal/policy/DecorView.java
+++ b/core/java/com/android/internal/policy/DecorView.java
@@ -78,6 +78,7 @@
 
 import static android.app.ActivityManager.StackId;
 import static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID;
+import static android.app.ActivityManager.StackId.PINNED_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;
@@ -2060,8 +2061,11 @@
         if (StackId.hasWindowShadow(mStackId) && !isResizing()) {
             elevation = hasWindowFocus() ?
                     DECOR_SHADOW_FOCUSED_HEIGHT_IN_DIP : DECOR_SHADOW_UNFOCUSED_HEIGHT_IN_DIP;
+            // Add a maximum shadow height value to the top level view.
+            // Note that pinned stack doesn't have focus
+            // so maximum shadow height adjustment isn't needed.
             // TODO(skuhne): Remove this if clause once b/22668382 got fixed.
-            if (!mAllowUpdateElevation) {
+            if (!mAllowUpdateElevation && mStackId != PINNED_STACK_ID) {
                 elevation = DECOR_SHADOW_FOCUSED_HEIGHT_IN_DIP;
             }
             // Convert the DP elevation into physical pixels.
diff --git a/core/java/com/android/internal/view/FloatingActionMode.java b/core/java/com/android/internal/view/FloatingActionMode.java
index b44baa2..ccdb024 100644
--- a/core/java/com/android/internal/view/FloatingActionMode.java
+++ b/core/java/com/android/internal/view/FloatingActionMode.java
@@ -24,6 +24,8 @@
 import android.view.MenuItem;
 import android.view.View;
 import android.view.ViewConfiguration;
+import android.view.ViewGroup;
+import android.view.ViewParent;
 
 import com.android.internal.R;
 import com.android.internal.util.Preconditions;
@@ -165,7 +167,17 @@
         checkToolbarInitialized();
 
         mContentRectOnScreen.set(mContentRect);
-        mContentRectOnScreen.offset(mViewPositionOnScreen[0], mViewPositionOnScreen[1]);
+
+        // Offset the content rect into screen coordinates, taking into account any transformations
+        // that may be applied to the originating view or its ancestors.
+        final ViewParent parent = mOriginatingView.getParent();
+        if (parent instanceof ViewGroup) {
+            ((ViewGroup) parent).getChildVisibleRect(
+                    mOriginatingView, mContentRectOnScreen, null /* offset */);
+            mContentRectOnScreen.offset(mRootViewPositionOnScreen[0], mRootViewPositionOnScreen[1]);
+        } else {
+            mContentRectOnScreen.offset(mViewPositionOnScreen[0], mViewPositionOnScreen[1]);
+        }
 
         if (isContentRectWithinBounds()) {
             mFloatingToolbarVisibilityHelper.setOutOfBounds(false);
diff --git a/core/java/com/android/internal/widget/FloatingToolbar.java b/core/java/com/android/internal/widget/FloatingToolbar.java
index 1848fe8..bc12391 100644
--- a/core/java/com/android/internal/widget/FloatingToolbar.java
+++ b/core/java/com/android/internal/widget/FloatingToolbar.java
@@ -592,9 +592,11 @@
         private void refreshCoordinatesAndOverflowDirection(Rect contentRectOnScreen) {
             refreshViewPort();
 
-            int x = contentRectOnScreen.centerX() - mPopupWindow.getWidth() / 2;
-            // Update x so that the toolbar isn't rendered behind the nav bar in landscape.
-            x = Math.max(0, Math.min(x, mViewPortOnScreen.right - mPopupWindow.getWidth()));
+            // Initialize x ensuring that the toolbar isn't rendered behind the nav bar in
+            // landscape.
+            final int x = Math.min(
+                    contentRectOnScreen.centerX() - mPopupWindow.getWidth() / 2,
+                    mViewPortOnScreen.right - mPopupWindow.getWidth());
 
             final int y;
 
@@ -684,7 +686,8 @@
             int rootViewTopOnWindow = mTmpCoords[1];
             int windowLeftOnScreen = rootViewLeftOnScreen - rootViewLeftOnWindow;
             int windowTopOnScreen = rootViewTopOnScreen - rootViewTopOnWindow;
-            mCoordsOnWindow.set(x - windowLeftOnScreen, y - windowTopOnScreen);
+            mCoordsOnWindow.set(
+                    Math.max(0, x - windowLeftOnScreen), Math.max(0, y - windowTopOnScreen));
         }
 
         /**
diff --git a/core/res/res/drawable-nodpi/default_wallpaper.png b/core/res/res/drawable-nodpi/default_wallpaper.png
index e9c4d5c..91ad252 100644
--- a/core/res/res/drawable-nodpi/default_wallpaper.png
+++ b/core/res/res/drawable-nodpi/default_wallpaper.png
Binary files differ
diff --git a/core/res/res/drawable-sw600dp-nodpi/default_wallpaper.png b/core/res/res/drawable-sw600dp-nodpi/default_wallpaper.png
index 9f3efa5..af8e251 100644
--- a/core/res/res/drawable-sw600dp-nodpi/default_wallpaper.png
+++ b/core/res/res/drawable-sw600dp-nodpi/default_wallpaper.png
Binary files differ
diff --git a/core/res/res/drawable-sw720dp-nodpi/default_wallpaper.png b/core/res/res/drawable-sw720dp-nodpi/default_wallpaper.png
index 8199e70..cb00d82 100644
--- a/core/res/res/drawable-sw720dp-nodpi/default_wallpaper.png
+++ b/core/res/res/drawable-sw720dp-nodpi/default_wallpaper.png
Binary files differ
diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml
index 4d86a92..14c17f3 100644
--- a/core/res/res/values/symbols.xml
+++ b/core/res/res/values/symbols.xml
@@ -2530,6 +2530,9 @@
   <java-symbol type="string" name="profile_encrypted_message" />
   <java-symbol type="drawable" name="ic_user_secure" />
 
+  <java-symbol type="string" name="android_upgrading_notification_title" />
+  <java-symbol type="string" name="android_upgrading_notification_body" />
+
   <java-symbol type="string" name="usb_mtp_launch_notification_title" />
   <java-symbol type="string" name="usb_mtp_launch_notification_description" />
 
diff --git a/data/etc/platform.xml b/data/etc/platform.xml
index 8a7d39b..a26850f 100644
--- a/data/etc/platform.xml
+++ b/data/etc/platform.xml
@@ -172,6 +172,10 @@
          access while in power save mode, even if they aren't in the foreground. -->
     <allow-in-power-save-except-idle package="com.android.providers.downloads" />
 
+    <!-- These are the standard packages that are white-listed to always have internet
+         access while in data mode, even if they aren't in the foreground. -->
+    <allow-in-data-usage-save package="com.android.providers.downloads" />
+
     <!-- These are the packages that are white-listed to be able to run as system user -->
     <system-user-whitelisted-app package="com.android.settings" />
 
diff --git a/data/sounds/alarms/material/ogg/Awaken_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Awaken_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..47b1d34
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Awaken_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Bounce_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Bounce_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..6af4d70
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Bounce_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Drip_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Drip_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..de3eec2
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Drip_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Gallop_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Gallop_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..98549b3
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Gallop_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Nudge_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Nudge_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..7a3d7ed
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Nudge_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Orbit_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Orbit_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..52e3918
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Orbit_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Rise_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Rise_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..a2d00cc
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Rise_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Sway_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Sway_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..273728a
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Sway_OG7_1ch_48k.ogg
Binary files differ
diff --git a/data/sounds/alarms/material/ogg/Wag_OG7_1ch_48k.ogg b/data/sounds/alarms/material/ogg/Wag_OG7_1ch_48k.ogg
new file mode 100755
index 0000000..f61d5b9
--- /dev/null
+++ b/data/sounds/alarms/material/ogg/Wag_OG7_1ch_48k.ogg
Binary files differ
diff --git a/docs/html/_redirects.yaml b/docs/html/_redirects.yaml
index adb31b8..545923f 100644
--- a/docs/html/_redirects.yaml
+++ b/docs/html/_redirects.yaml
@@ -24,11 +24,11 @@
 - from: /tools/debugging/debugging-projects-cmdline.html
   to: /tools/debugging/index.html
 - from: /sdk/compatibility-library.html
-  to: /tools/support-library/index.html
+  to: /go/libraries/support-library/index.html
 - from: /tools/extras/support-library.html
-  to: /tools/support-library/index.html
+  to: /go/libraries/support-library/index.html
 - from: /training/basics/fragments/support-lib.html
-  to: /tools/support-library/setup.html
+  to: /go/libraries/support-library/setup.html
 - from: /sdk/eclipse-adt.html
   to: /tools/sdk/eclipse-adt.html
 - from: /sdk/RELEASENOTES.html
@@ -72,13 +72,11 @@
 - from: /tools/publishing/app-signing-eclipse.html
   to: /tools/help/adt.html
 - from: /tools/help/uiautomator/.*
-  to: /tools/testing-support-library/index.html
+  to: /go/libraries/testing-support/library/
 - from: /tools/testing/testing_ui.html
   to: /training/testing/ui-testing/index.html
 - from: /tools/testing/activity_test.html
   to: /training/testing/ui-testing/index.html
-- from: /tools/data-binding/index.html
-  to: /tools/data-binding/guide.html
 - from: /tools/testing/what_to_test.html
   to: /distribute/essentials/quality/core.html
 - from: /tools/testing/testing_accessibility.html
@@ -725,3 +723,14 @@
   to: https://commondatastorage.googleapis.com/androiddevelopers/shareables/
 - from: /downloads/
   to: https://commondatastorage.googleapis.com/androiddevelopers/
+
+# Redirects for the new go/libraries/ area
+
+- from: /tools/support-library
+  to: /go/libraries/support-library
+
+- from: /tools/data-binding/...
+  to: /go/libraries/data-binding
+
+- from: /tools/testing-support-library
+  to: /go/libraries/testing-support-library
diff --git a/docs/html/about/_book.yaml b/docs/html/about/_book.yaml
index 04150bd..fdbe53f 100644
--- a/docs/html/about/_book.yaml
+++ b/docs/html/about/_book.yaml
@@ -16,13 +16,19 @@
     path: /about/versions/android-5.1.html
   - title: Android 5.0 APIs
     path: /about/versions/android-5.0.html
-    custom_link_attributes:
-    - es-lang="API de Android 5.0"
-    - ja-lang="Android 5.0 API"
-    - ko-lang="Android 5.0 API"
-    - ru-lang="API для Android 5.0"
-    - zh-cn-lang="Android 5.0 API"
-    - zh-tw-lang="Android 5.0 API"
+    path_attributes:
+    - name: es-lang
+      value: API de Android 5.0
+    - name: ja-lang
+      value: Android 5.0 API
+    - name: ko-lang
+      value: Android 5.0 API
+    - name: ru-lang
+      value: API для Android 5.0
+    - name: zh-cn-lang
+      value: Android 5.0 API
+    - name: zh-tw-lang
+      value: Android 5.0 API
   - title: Android 5.0 Changes
     path: /about/versions/android-5.0-changes.html
 
diff --git a/docs/html/design/_book.yaml b/docs/html/design/_book.yaml
index 4575475..df5406f 100644
--- a/docs/html/design/_book.yaml
+++ b/docs/html/design/_book.yaml
@@ -4,24 +4,35 @@
   section:
   - title: Design Principles
     path: /design/get-started/principles.html
-    custom_link_attributes:
-    - es-lang="Principios de diseño para Android"
-    - ja-lang="Android デザイン指針"
-    - ko-lang="Android 디자인 원칙"
-    - pt-br-lang="Princípios de projeto para Android"
-    - ru-lang="Принципы проектирования Android"
-    - zh-cn-lang="Android 设计原则"
-    - zh-tw-lang="Android 設計原則"
+    path_attributes:
+    - name: es-lang
+      value: Principios de diseño para Android
+    - name: ja-lang
+      value: Android デザイン指針
+    - name: ko-lang
+      value: Android 디자인 원칙
+    - name: pt-br-lang
+      value: Princípios de projeto para Android
+    - name: ru-lang
+      value: Принципы проектирования Android
+    - name: zh-cn-lang
+      value: Android 设计原则
+    - name: zh-tw-lang
+      value: Android 設計原則
   - title: New in Android
     path: /design/patterns/new.html
 
 - title: Material for Android
   path: /design/material/index.html
-  custom_link_attributes:
-  - ja-lang="マテリアル デザイン"
-  - ko-lang="머티어리얼 디자인"
-  - zh-cn-lang="材料设计"
-  - zh-tw-lang="材料設計"
+  path_attributes:
+  - name: ja-lang
+    value: マテリアル デザイン
+  - name: ko-lang
+    value: 머티어리얼 디자인
+  - name: zh-cn-lang
+    value: 材料设计
+  - name: zh-tw-lang
+    value: 材料設計
 
 - title: Devices
   path: /design/devices.html
@@ -64,24 +75,38 @@
     path: /design/style/devices-displays.html
   - title: Navigation
     path: /design/patterns/navigation.html
-    custom_link_attributes:
-    - es-lang="Navegación con los botones Back y Up"
-    - ja-lang="Back と Up を使用したナビゲーション"
-    - ko-lang="뒤로 및 위로 탐색 기능이 포함된 탐색"
-    - pt-br-lang="Navegação com Voltar e Para cima"
-    - ru-lang="Навигация с помощью кнопок \"Назад\" и \"Вверх\""
-    - zh-cn-lang="使用返回和向上导航"
-    - zh-tw-lang="使用 [返回] 及 [上一層] 導覽"
+    path_attributes:
+    - name: es-lang
+      value: Navegación con los botones Back y Up
+    - name: ja-lang
+      value: Back と Up を使用したナビゲーション
+    - name: ko-lang
+      value: 뒤로 및 위로 탐색 기능이 포함된 탐색
+    - name: pt-br-lang
+      value: Navegação com Voltar e Para cima
+    - name: ru-lang
+      value: Навигация с помощью кнопок "Назад" и "Вверх"
+    - name: zh-cn-lang
+      value: 使用返回和向上导航
+    - name: zh-tw-lang
+      value: 使用 [返回] 及 [上一層] 導覽
   - title: Notifications
     path: /design/patterns/notifications.html
-    custom_link_attributes:
-    - es-lang="Notificaciones"
-    - ja-lang="通知"
-    - ko-lang="알림"
-    - pt-br-lang="Notificações"
-    - ru-lang="Уведомления"
-    - zh-cn-lang="通知"
-    - zh-tw-lang="通知"
+    path_attributes:
+    - name: es-lang
+      value: Notificaciones
+    - name: ja-lang
+      value: 通知
+    - name: ko-lang
+      value: 알림
+    - name: pt-br-lang
+      value: Notificações
+    - name: ru-lang
+      value: Уведомления
+    - name: zh-cn-lang
+      value: 通知
+    - name: zh-tw-lang
+      value: 通知
   - title: Widgets
     path: /design/patterns/widgets.html
   - title: Swipe Views
@@ -90,14 +115,21 @@
     path: /design/patterns/fullscreen.html
   - title: Confirming & Acknowledging
     path: /design/patterns/confirming-acknowledging.html
-    custom_link_attributes:
-    - es-lang="Confirmación y reconocimiento"
-    - ja-lang="確認と通知"
-    - ko-lang="확인 및 승인하기"
-    - pt-br-lang="Confirmação e reconhecimento"
-    - ru-lang="Подтверждение и уведомление"
-    - zh-cn-lang="确认和确知"
-    - zh-tw-lang="確認及確認完成"
+    path_attributes:
+    - name: es-lang
+      value: Confirmación y reconocimiento
+    - name: ja-lang
+      value: 確認と通知
+    - name: ko-lang
+      value: 확인 및 승인하기
+    - name: pt-br-lang
+      value: Confirmação e reconhecimento
+    - name: ru-lang
+      value: Подтверждение и уведомление
+    - name: zh-cn-lang
+      value: 确认和确知
+    - name: zh-tw-lang
+      value: 確認及確認完成
   - title: Pure Android
     path: /design/patterns/pure-android.html
   - title: Compatibility
diff --git a/docs/html/distribute/essentials/_book.yaml b/docs/html/distribute/essentials/_book.yaml
index e8b7811..6a2c8f5 100644
--- a/docs/html/distribute/essentials/_book.yaml
+++ b/docs/html/distribute/essentials/_book.yaml
@@ -1,13 +1,15 @@
 toc:
 - title: Core App Quality
   path: /distribute/essentials/quality/core.html
-  custom_link_attributes:
-  - zh-cn-lang="应用的核心质量"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 应用的核心质量
 
 - title: Tablet App Quality
   path: /distribute/essentials/quality/tablets.html
-  custom_link_attributes:
-  - zh-cn-lang="平板电脑应用的质量"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 平板电脑应用的质量
 
 - title: Wear App Quality
   path: /distribute/essentials/quality/wear.html
@@ -20,31 +22,36 @@
 
 - title: Launch Checklist
   path: /distribute/tools/launch-checklist.html
-  custom_link_attributes:
-  - zh-cn-lang="发布检查清单"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 发布检查清单
 
 - title: Localization Checklist
   path: /distribute/tools/localization-checklist.html
-  custom_link_attributes:
-  - zh-cn-lang="本地化检查清单"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 本地化检查清单
 
 - title: Brand Guidelines
   path: /distribute/tools/promote/brand.html
-  custom_link_attributes:
-  - zh-cn-lang="品牌指南"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 品牌指南
 
 - title: Device Art Generator
   path: /distribute/tools/promote/device-art.html
 
 - title: Google Play Badges
   path: https://play.google.com/intl/en_us/badges/
-  custom_link_attributes:
-  - zh-cn-lang="Google Play 徽章生成器"
+  path_attributes:
+  - name: zh-cn-lang
+    value: Google Play 徽章生成器
 
 - title: Linking to Your Products
   path: /distribute/tools/promote/linking.html
-  custom_link_attributes:
-  - zh-cn-lang="链接到您的商品"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 链接到您的商品
 
 - title: Alternative Distribution
   path: /distribute/tools/open-distribution.html
diff --git a/docs/html/distribute/googleplay/_book.yaml b/docs/html/distribute/googleplay/_book.yaml
index 009d1c07..ede18f4 100644
--- a/docs/html/distribute/googleplay/_book.yaml
+++ b/docs/html/distribute/googleplay/_book.yaml
@@ -1,75 +1,119 @@
 toc:
 - title: The Google Play Opportunity
   path: /distribute/googleplay/about.html
-  custom_link_attributes:
-  - es-lang="La oportunidad de Google Play"
-  - ja-lang="Google Play の可能性"
-  - ko-lang="Google Play 활용 기회"
-  - pt-br-lang="A oportunidade do Google Play"
-  - ru-lang="Возможности Google Play"
-  - zh-cn-lang="Google Play 蕴藏的机会"
-  - zh-tw-lang="Google Play商機"
+  path_attributes:
+  - name: es-lang
+    value: La oportunidad de Google Play
+  - name: ja-lang
+    value: Google Play の可能性
+  - name: ko-lang
+    value: Google Play 활용 기회
+  - name: pt-br-lang
+    value: A oportunidade do Google Play
+  - name: ru-lang
+    value: Возможности Google Play
+  - name: zh-cn-lang
+    value: Google Play 蕴藏的机会
+  - name: zh-tw-lang
+    value: Google Play商機
 
 - title: Get Started with Publishing
   path: /distribute/googleplay/start.html
-  custom_link_attributes:
-  - es-lang="Comienza a publicar"
-  - ja-lang="アプリを公開する"
-  - ko-lang="게시 시작하기"
-  - pt-br-lang="Introdução à publicação"
-  - ru-lang="Первые шаги в публикациях"
-  - zh-cn-lang="开始发布"
-  - zh-tw-lang="開始發行"
+  path_attributes:
+  - name: es-lang
+    value: Comienza a publicar
+  - name: ja-lang
+    value: アプリを公開する
+  - name: ko-lang
+    value: 게시 시작하기
+  - name: pt-br-lang
+    value: Introdução à publicação
+  - name: ru-lang
+    value: Первые шаги в публикациях
+  - name: zh-cn-lang
+    value: 开始发布
+  - name: zh-tw-lang
+    value: 開始發行
 
 - title: Developer Console
   path: /distribute/googleplay/developer-console.html
-  custom_link_attributes:
-  - es-lang="Consola para desarrolladores"
-  - ja-lang="デベロッパー コンソール"
-  - ko-lang="개발자 콘솔"
-  - pt-br-lang="Console do Desenvolvedor"
-  - ru-lang="Консоль разработчика"
-  - zh-cn-lang="开发者控制台"
+  path_attributes:
+  - name: es-lang
+    value: Consola para desarrolladores
+  - name: ja-lang
+    value: デベロッパー コンソール
+  - name: ko-lang
+    value: 개발자 콘솔
+  - name: pt-br-lang
+    value: Console do Desenvolvedor
+  - name: ru-lang
+    value: Консоль разработчика
+  - name: zh-cn-lang
+    value: 开发者控制台
 
 - title: Distribute to Android Wear
   path: /distribute/googleplay/wear.html
-  custom_link_attributes:
-  - es-lang="Distribución para Android Wear"
-  - ja-lang="Android Wear への配布"
-  - ko-lang="Android Wear에 배포"
-  - pt-br-lang="Distribuindo para Android Wear"
-  - ru-lang="Распространение приложений Android Wear"
-  - zh-cn-lang="分发到 Android Wear"
-  - zh-tw-lang="散佈至 Android Wear"
+  path_attributes:
+  - name: es-lang
+    value: Distribución para Android Wear
+  - name: ja-lang
+    value: Android Wear への配布
+  - name: ko-lang
+    value: Android Wear에 배포
+  - name: pt-br-lang
+    value: Distribuindo para Android Wear
+  - name: ru-lang
+    value: Распространение приложений Android Wear
+  - name: zh-cn-lang
+    value: 分发到 Android Wear
+  - name: zh-tw-lang
+    value: 散佈至 Android Wear
 
 - title: Distribute to Android TV
   path: /distribute/googleplay/tv.html
-  custom_link_attributes:
-  - es-lang="Distribución para Android TV"
-  - ja-lang="Android TV への配布"
-  - ko-lang="Android TV에 배포"
-  - pt-br-lang="Distribuindo para Android TV"
-  - ru-lang="Распространение приложений в Android TV"
-  - zh-cn-lang="分发到 Android TV"
-  - zh-tw-lang="散佈至 Android 電視"
+  path_attributes:
+  - name: es-lang
+    value: Distribución para Android TV
+  - name: ja-lang
+    value: Android TV への配布
+  - name: ko-lang
+    value: Android TV에 배포
+  - name: pt-br-lang
+    value: Distribuindo para Android TV
+  - name: ru-lang
+    value: Распространение приложений в Android TV
+  - name: zh-cn-lang
+    value: 分发到 Android TV
+  - name: zh-tw-lang
+    value: 散佈至 Android 電視
 
 - title: Distribute to Android Auto
   path: /distribute/googleplay/auto.html
-  custom_link_attributes:
-  - es-lang="Distribución para Android Auto"
-  - ja-lang="Android Auto への配布"
-  - ko-lang="Android Auto에 배포"
-  - pt-br-lang="Distribuindo para o Android Auto"
-  - ru-lang="Распространение приложений для Android Auto"
-  - zh-cn-lang="分发到 Android Auto"
-  - zh-tw-lang="散佈至 Android Auto"
+  path_attributes:
+  - name: es-lang
+    value: Distribución para Android Auto
+  - name: ja-lang
+    value: Android Auto への配布
+  - name: ko-lang
+    value: Android Auto에 배포
+  - name: pt-br-lang
+    value: Distribuindo para o Android Auto
+  - name: ru-lang
+    value: Распространение приложений для Android Auto
+  - name: zh-cn-lang
+    value: 分发到 Android Auto
+  - name: zh-tw-lang
+    value: 散佈至 Android Auto
 
 - title: Designed for Families
   path: /distribute/googleplay/families/about.html
-  custom_link_attributes:
-  - es-lang="Diseñado para la familia"
-  - ru-lang="Для всей семьи"
-  - zh-cn-lang="为家庭设计"
+  path_attributes:
+  - name: es-lang
+    value: Diseñado para la familia
+  - name: ru-lang
+    value: Для всей семьи
+  - name: zh-cn-lang
+    value: 为家庭设计
 
 - title: Google Play for Work
   path: /distribute/googleplay/work/about.html
@@ -90,11 +134,18 @@
 
 - title: Find Success on Google Play
   path: /distribute/googleplay/guide.html
-  custom_link_attributes:
-  - es-lang="Cómo tener éxito en Google Play"
-  - ja-lang="Google Play で成功を手にする"
-  - ko-lang="Google Play에서 성공 모색"
-  - pt-br-lang="Obtendo sucesso no Google Play"
-  - ru-lang="Найдите свой путь к успеху в Google Play"
-  - zh-cn-lang="在 Google Play 上取得成功"
-  - zh-tw-lang="在 Google Play 上尋找成功"
+  path_attributes:
+  - name: es-lang
+    value: Cómo tener éxito en Google Play
+  - name: ja-lang
+    value: Google Play で成功を手にする
+  - name: ko-lang
+    value: Google Play에서 성공 모색
+  - name: pt-br-lang
+    value: Obtendo sucesso no Google Play
+  - name: ru-lang
+    value: Найдите свой путь к успеху в Google Play
+  - name: zh-cn-lang
+    value: 在 Google Play 上取得成功
+  - name: zh-tw-lang
+    value: 在 Google Play 上尋找成功
diff --git a/docs/html/distribute/tools/_book.yaml b/docs/html/distribute/tools/_book.yaml
index 57e03ba..4064c34 100644
--- a/docs/html/distribute/tools/_book.yaml
+++ b/docs/html/distribute/tools/_book.yaml
@@ -1,31 +1,36 @@
 toc:
 - title: Launch Checklist
   path: /distribute/tools/launch-checklist.html
-  custom_link_attributes:
-  - zh-cn-lang="发布检查清单"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 发布检查清单
 
 - title: Localization Checklist
   path: /distribute/tools/localization-checklist.html
-  custom_link_attributes:
-  - zh-cn-lang="本地化检查清单"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 本地化检查清单
 
 - title: Device Art Generator
   path: /distribute/tools/promote/device-art.html
 
 - title: Google Play Badges
   path: /distribute/tools/promote/badges.html
-  custom_link_attributes:
-  - zh-cn-lang="Google Play 徽章生成器"
+  path_attributes:
+  - name: zh-cn-lang
+    value: Google Play 徽章生成器
 
 - title: Linking to Your Products
   path: /distribute/tools/promote/linking.html
-  custom_link_attributes:
-  - zh-cn-lang="链接到您的商品"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 链接到您的商品
 
 - title: Brand Guidelines
   path: /distribute/tools/promote/brand.html
-  custom_link_attributes:
-  - zh-cn-lang="品牌指南"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 品牌指南
 
 - title: Alternative Distribution
   path: /distribute/tools/open-distribution.html
diff --git a/docs/html/go/libraries/_book.yaml b/docs/html/go/libraries/_book.yaml
new file mode 100644
index 0000000..209dae5
--- /dev/null
+++ b/docs/html/go/libraries/_book.yaml
@@ -0,0 +1,17 @@
+toc:
+- title: Support Library
+  path: /tools/support-library/index.html
+  section:
+  - title: Features
+    path: /tools/support-library/features.html
+  - title: Setup
+    path: /tools/support-library/setup.html
+
+- title: Data Binding Library
+  path: /tools/data-binding/guide.html
+
+- title: Testing Support Library
+  path: /tools/testing-support-library/index.html
+  section:
+  - title: API Reference
+    path: /reference/android/support/test/package-summary.html
diff --git a/docs/html/tools/data-binding/guide.jd b/docs/html/go/libraries/data-binding/index.jd
similarity index 99%
rename from docs/html/tools/data-binding/guide.jd
rename to docs/html/go/libraries/data-binding/index.jd
index 8bbd833..ca8784e 100644
--- a/docs/html/tools/data-binding/guide.jd
+++ b/docs/html/go/libraries/data-binding/index.jd
@@ -1,4 +1,5 @@
-page.title=Data Binding Guide
+page.title=Data Binding Library
+page.metaDescription=The Data Binding Library enables you to write declarative layouts.
 page.tags="databinding", "layouts"
 @jd:body
 
diff --git a/docs/html/go/libraries/index.jd b/docs/html/go/libraries/index.jd
new file mode 100644
index 0000000..2831d15
--- /dev/null
+++ b/docs/html/go/libraries/index.jd
@@ -0,0 +1,14 @@
+page.title=Android Libraries
+
+@jd:body
+
+<p>This section describes several useful Android libraries that are not
+included with the Android Framework.</p>
+
+<div class="dynamic-grid">
+  <div class="resource-widget resource-flow-layout landing col-12"
+    data-query="collection:go/libraries"
+    data-cardSizes="6x6"
+    data-maxResults="6">
+  </div>
+</div>
diff --git a/docs/html/tools/support-library/features.jd b/docs/html/go/libraries/support-library/features.jd
similarity index 98%
rename from docs/html/tools/support-library/features.jd
rename to docs/html/go/libraries/support-library/features.jd
index a5f343e..089357a 100755
--- a/docs/html/tools/support-library/features.jd
+++ b/docs/html/go/libraries/support-library/features.jd
@@ -34,11 +34,11 @@
 
     <h2>See also</h2>
     <ol>
-      <li><a href="{@docRoot}tools/support-library/index.html#revisions">
+      <li><a href="{@docRoot}go/libraries/support-library/index.html#revisions">
         Support Library Revisions</a></li>
-      <li><a href="{@docRoot}tools/support-library/setup.html">
+      <li><a href="{@docRoot}go/libraries/support-library/setup.html">
         Support Library Setup</a></li>
-      <li><a href="{@docRoot}tools/testing-support-library/index.html">
+      <li><a href="{@docRoot}go/libraries/testing-support-library/index.html">
         Testing Support Library</a></li>
     </ol>
 
diff --git a/docs/html/tools/support-library/index.jd b/docs/html/go/libraries/support-library/index.jd
similarity index 93%
rename from docs/html/tools/support-library/index.jd
rename to docs/html/go/libraries/support-library/index.jd
index 3afd7ac..61f0bc2 100644
--- a/docs/html/tools/support-library/index.jd
+++ b/docs/html/go/libraries/support-library/index.jd
@@ -1,4 +1,5 @@
 page.title=Support Library
+page.metaDescription=The Android Support Library offers backward-compatible versions of a number of features that are not built into the framework.
 
 @jd:body
 
@@ -8,7 +9,11 @@
     <h2>In this document</h2>
     <ol>
       <li><a href="#overview">Overview</a></li>
-      <li><a href="#revisions">Revisions</a></li>
+      <li><a href="#backward">Backward Compatibility</a></li>
+      <li><a href="#layout-patterns">Support for General Layout Patterns</a></li>
+      <li><a href="#form-factors">Support for Different Form Factors</a></li>
+      <li><a href="#utils">General Utilities</a></li>
+      <li><a href="#revisions">Support Library Revision History</a></li>
     </ol>
 
     <h2>See also</h2>
@@ -22,39 +27,161 @@
   </div>
 </div>
 
-<p>The Android Support Library package is a set of code libraries that provide
-  backward-compatible versions of Android framework APIs as well as features that are only available
-  through the library APIs. Each Support Library is backward-compatible to a specific Android API
-  level. This design means that your applications can use the libraries' features and still be
-  compatible with devices running Android 1.6 (API level 4) and up.</p>
-
-<p>This guide provides information about what features are enabled by the Support Libraries,
-  how to use them in your development environment and information about library releases.</p>
-
+<p>
+  The Android Support Library offers a number of features that are not built
+  into the framework. These libraries offer backward-compatible versions of
+  new features, provide useful UI elements that are not included in the
+  framework, and provide a range of utilities that apps can draw on.
+</p>
 
 <h2 id="overview">Overview</h2>
 
-<p>Including the Support Libraries in your Android project is considered a best practice for
-  application developers, depending on the range of platform versions your app is targeting
-  and the APIs that it uses. Using the features the libraries provide can help you improve the look
-  of your application, increase performance and broaden the reach of your application to more users.
-  If you use the Android
-  <a href="{@docRoot}tools/projects/templates.html">code template</a> tools, you will notice that
-  all the Android application templates include one or more of the Support Libraries by default.</p>
+<p>
+  In many cases, a feature may be valuable to many app developers, but not
+  appropriate to include in the Android framework itself. For example, an app
+  might only need a feature for specialized use cases, such as to smooth the
+  transition between different versions of the Android system.
+</p>
 
-<p>The Support Libraries each target a base Android API level and each provides a different set
-  of features. In order to effectively use the libraries, it is important to consider what features
-  you want to support and understand what features are supported by each library at what Android
-  API level. To get started, review the
-  <a href="{@docRoot}tools/support-library/features.html">Support Library Features</a> guide.
-  After that, go to the
-  <a href="{@docRoot}tools/support-library/setup.html">Support Library Setup</a> topic to
-  learn how to incorporate the Support Libraries into your application. For more details
-  about Support Library APIs, see the {@link android.support.v4.app android.support}
-  packages in the API reference.</p>
+<p>
+  To address these situations, the Android SDK includes several libraries
+  collectively called the <em>Android Support Library</em>. App developers
+  can include any of these libraries if they want to incorporate the
+  library functionality into their apps.
+</p>
+
+<p>
+  Support libraries provide a range of different features:
+</p>
+
+<ul>
+  <li>
+    <a href="#backward">Backward-compatible</a> versions of framework
+    components.
+  </li>
+
+  <li>UI elements to implement the recommended Android <a href=
+  "#layout-patterns">layout patterns</a>.
+  </li>
+
+  <li>Support for different <a href="#form-factors">form factors</a>.
+  </li>
+
+  <li>Miscellaneous <a href="#utils">utility</a> functions.
+  </li>
+</ul>
+
+<h2 id="backward">Backward Compatibility</h2>
+
+<div class="figure" style="width:300px">
+  <img src="{@docRoot}images/tools/support-library/appbar-kitkat.png"
+    srcset="{@docRoot}images/tools/support-library/appbar-kitkat.png 1x,
+        {@docRoot}images/tools/support-library/appbar-kitkat_2x.png 2x"
+    alt="" width="300">
+  <p class="img-caption">
+    <strong>Figure 1.</strong> Because this app uses support library UI
+    elements its interface incorporates material design principles, even though
+    it is running on Android 4.4, which does not include native support for
+    material design.
+  </p>
+</div>
+
+<p>
+  Support libraries allow apps running on older versions of the Android
+  platform to support features made available on newer versions of the
+  platform. For example, an app running on a version of Android lower than 5.0
+  (API level 21) that relies on framework classes cannot display
+  material-design elements, as that version of the Android framework doesn't
+  support material design. However, if the app incorporates the Support
+  Library's <a href="{@docRoot}tools/support-library/features.html">appcompat
+  library</a>, the app has access to many of the features available in API
+  level 21, including support for material design. As a result, your app can
+  deliver a more consistent experience across a broader range of platform
+  versions.
+</p>
 
 
-<h2 id="revisions">Revisions</h2>
+<p>
+  In some cases, the support library version of a class depends as much as
+  possible on the functionality that the framework provides. In these cases,
+  if an app calls one of the support class's methods, the support library's
+  behavior depends on what version of Android the app is running on. If the
+  framework provides the necessary functionality, the support library calls on
+  the framework to perform the task. If the app is running on an earlier
+  version of Android, and the framework doesn't expose the needed
+  functionality, the support library may try to provide the functionality
+  itself, or may act as a no-op. In either case, the app generally doesn't
+  need to check what version of Android it's running on; instead, the app
+  can rely on the support library to do those checks and choose appropriate
+  behavior. Generally, classes whose names end in
+  <code>…Compat</code> (like {@link android.support.v4.app.ActivityCompat})
+  behave this way.
+</p>
+
+<p>
+  In other cases, the support library class provides a complete, standalone
+  version of a framework class that does not rely on the availability of
+  any framework APIs. These
+  methods provide consistent behavior across all supported platforms.
+</p>
+
+<p>
+  In either case, the app does not need to check the system version at run
+  time. The app can rely on the support library class to do the appropriate
+  system checks, and modify its behavior as necessary.
+</p>
+
+<h2 id="layout-patterns">Support for General Layout Patterns</h2>
+
+<p>
+  Support libraries provide user interface elements not offered by
+  the Android framework. For example, the Android Support Library offers additional
+  layout classes, like {@link android.support.v4.widget.DrawerLayout}. These
+  classes follow recommended Android design practices; for example, the Design
+  Library follows the principles of material design in a way that works across
+  many versions of Android.
+</p>
+
+<p>
+  By using these support library classes, you can avoid having to reinvent the
+  wheel; if your app has a particular user interface requirement, you can draw
+  on existing code, which provides a user interface that users will already be
+  familiar with. These elements also help you build an app that looks and feels
+  like a part of the Android ecosystem. For example, many apps need to display
+  arbitrarily long lists of elements, and need to be able to quickly and
+  efficiently reuse those elements as the list changes; this might be a list of
+  emails, contacts, music albums, and so on. Those apps can use the support
+  library {@link android.support.v7.widget.RecyclerView} widget to display the
+  list. This saves the app developer from having to develop the list from
+  scratch, and also ensures that the user will see a list that looks and
+  behaves like lists in other apps.
+</p>
+
+<h2 id="form-factors">Support for Different Form Factors</h2>
+
+<p>
+  The Android SDK provides libraries for a number of different form factors,
+  such as TV and wearables. An app can depend on the appropriate support
+  library to provide functionality across a wide range of platform versions,
+  and can provide content on external screens, speakers, and other destination
+  devices.
+</p>
+
+<h2 id="utils">General Utilities</h2>
+
+<p>
+  The Android Support Library provides backward-compatible utility functions.
+  Apps can use these utility functions to provide an appropriate user
+  experience across a wide range of Android system versions. For example,
+  support library permission methods behave appropriately depending on what
+  platform version your app is running on. If the platform supports the
+  runtime permissions model, these methods request the appropriate permission
+  from the user; on platform versions that do not support the runtime
+  permissions model, the methods check whether the appropriate permission was
+  granted at install time.
+</p>
+
+<h2 id="revisions">Support Library Revision History</h2>
 
 <p>This section provides details about the Support Library package releases.</p>
 
diff --git a/docs/html/tools/support-library/setup.jd b/docs/html/go/libraries/support-library/setup.jd
similarity index 100%
rename from docs/html/tools/support-library/setup.jd
rename to docs/html/go/libraries/support-library/setup.jd
diff --git a/docs/html/tools/testing-support-library/index.jd b/docs/html/go/libraries/testing-support-library/index.jd
similarity index 99%
rename from docs/html/tools/testing-support-library/index.jd
rename to docs/html/go/libraries/testing-support-library/index.jd
index 35a3c7d..f69a35b7 100644
--- a/docs/html/tools/testing-support-library/index.jd
+++ b/docs/html/go/libraries/testing-support-library/index.jd
@@ -1,4 +1,5 @@
 page.title=Testing Support Library
+page.metaDescription=The Android Testing Support Library provides an extensive framework for testing Android apps.
 page.image=images/tools/studio-test-module.png
 
 @jd:body
diff --git a/docs/html/google/_book.yaml b/docs/html/google/_book.yaml
index 01efa4f..92357e9 100644
--- a/docs/html/google/_book.yaml
+++ b/docs/html/google/_book.yaml
@@ -1,17 +1,20 @@
 toc:
 - title: Google Play In-app Billing
   path: /google/play/billing/index.html
-  custom_link_attributes:
-  - zh-cn-lang="应用内结算"
+  path_attributes:
+  - name: zh-cn-lang
+    value: 应用内结算
   section:
   - title: Overview
     path: /google/play/billing/billing_overview.html
-    custom_link_attributes:
-    - zh-cn-lang="应用内结算概述"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 应用内结算概述
   - title: Version 3 API
     path: /google/play/billing/api.html
-    custom_link_attributes:
-    - zh-cn-lang="应用内结算 API"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 应用内结算 API
     section:
     - title: Implementing the API
       path: /google/play/billing/billing_integrate.html
@@ -23,29 +26,39 @@
     path: /google/play/billing/billing_promotions.html
   - title: Security and Design
     path: /google/play/billing/billing_best_practices.html
-    custom_link_attributes:
-    - zh-cn-lang="安全性和设计"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 安全性和设计
   - title: Testing In-app Billing
     path: /google/play/billing/billing_testing.html
-    custom_link_attributes:
-    - zh-cn-lang="测试应用内结算"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 测试应用内结算
   - title: Administering In-app Billing
     path: /google/play/billing/billing_admin.html
-    custom_link_attributes:
-    - zh-cn-lang="管理应用内结算"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 管理应用内结算
   - title: Version Notes
     path: /google/play/billing/versions.html
 
 - title: Filters on Google Play
   path: /google/play/filters.html
-  custom_link_attributes:
-  - es-lang="Filtros en Google Play"
-  - ja-lang="Google Play 上のフィルタ"
-  - ko-lang="Google Play 필터"
-  - pt-br-lang="Filtros no Google Play"
-  - ru-lang="Фильтры в Google Play"
-  - zh-cn-lang="Google Play 上的筛选器"
-  - zh-tw-lang="Google Play 上的篩選器"
+  path_attributes:
+  - name: es-lang
+    value: Filtros en Google Play
+  - name: ja-lang
+    value: Google Play 上のフィルタ
+  - name: ko-lang
+    value: Google Play 필터
+  - name: pt-br-lang
+    value: Filtros no Google Play
+  - name: ru-lang
+    value: Фильтры в Google Play
+  - name: zh-cn-lang
+    value: Google Play 上的筛选器
+  - name: zh-tw-lang
+    value: Google Play 上的篩選器
 
 - title: Google Play Developer API
   path: /google/play/developer-api.html
diff --git a/docs/html/guide/_book.yaml b/docs/html/guide/_book.yaml
index 5017376..4163f0f 100644
--- a/docs/html/guide/_book.yaml
+++ b/docs/html/guide/_book.yaml
@@ -365,6 +365,12 @@
   - title: App Install Location
     path: /guide/topics/data/install-location.html
 
+
+- title: Libraries
+  path: /go/libraries/index.html
+  section:
+  - include: /go/libraries/_book.yaml
+
 - title: Administration
   path: /guide/topics/admin/index.html
   section:
@@ -387,14 +393,21 @@
 
 - title: Best Practices
   path: /guide/practices/index.html
-  custom_link_attributes:
-  - de-lang="Bewährte Verfahren"
-  - es-lang="Prácticas recomendadas"
-  - fr-lang="Meilleures pratiques"
-  - it-lang="Best practice"
-  - ja-lang="ベスト プラクティス"
-  - zh-cn-lang="最佳实践"
-  - zh-tw-lang="最佳實務"
+  path_attributes:
+  - name: de-lang
+    value: Bewährte Verfahren
+  - name: es-lang
+    value: Prácticas recomendadas
+  - name: fr-lang
+    value: Meilleures pratiques
+  - name: it-lang
+    value: Best practice
+  - name: ja-lang
+    value: ベスト プラクティス
+  - name: zh-cn-lang
+    value: 最佳实践
+  - name: zh-tw-lang
+    value: 最佳實務
   section:
   - title: Supporting Multiple Screens
     path: /guide/practices/screens_support.html
diff --git a/docs/html/guide/guide_toc.cs b/docs/html/guide/guide_toc.cs
index 549a1b6..9257a76 100644
--- a/docs/html/guide/guide_toc.cs
+++ b/docs/html/guide/guide_toc.cs
@@ -121,7 +121,7 @@
       <li><a href="<?cs var:toroot ?>guide/topics/resources/overview.html">
           <span class="en">Overview</span>
         </a></li>
-        <li><a href="<?cs var:toroot ?>guide/topics/resources/providing-resources.html">
+      <li><a href="<?cs var:toroot ?>guide/topics/resources/providing-resources.html">
           <span class="en">Providing Resources</span>
         </a></li>
       <li><a href="<?cs var:toroot ?>guide/topics/resources/accessing-resources.html">
@@ -129,10 +129,13 @@
         </a></li>
       <li><a href="<?cs var:toroot ?>guide/topics/resources/runtime-changes.html">
             <span class="en">Handling Runtime Changes</span>
-          </a></li>
+        </a></li>
       <li><a href="<?cs var:toroot ?>guide/topics/resources/localization.html">
           <span class="en">Localization</span>
         </a></li>
+      <li><a href="<?cs var:toroot ?>guide/topics/resources/complex-xml-resources.html">
+          <span class="en">Complex XML Resources</span>
+        </a></li>
       <li class="nav-section">
         <div class="nav-section-header"><a href="<?cs var:toroot ?>guide/topics/resources/available-resources.html">
             <span class="en">Resource Types</span>
diff --git a/docs/html/guide/topics/resources/complex-xml-resources.jd b/docs/html/guide/topics/resources/complex-xml-resources.jd
new file mode 100644
index 0000000..66dcb58
--- /dev/null
+++ b/docs/html/guide/topics/resources/complex-xml-resources.jd
@@ -0,0 +1,117 @@
+page.title=Inline Complex XML Resources
+parent.title=Application Resources
+parent.link=index.html
+@jd:body
+
+<p>Certain resource types are a composition of multiple complex resources represented by XML files.
+One example is an animated vector drawable, which is a drawable resource encapsulating a vector
+drawable and an animation. This requires the use of at least three XML files.</p>
+
+<dl>
+
+<dt><code>res/drawable/avd.xml</code></dt>
+<dd>
+<pre class="stx">
+&lt;?xml version="1.0" encoding="utf-8"?&gt;
+&lt;animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
+    android:drawable="@drawable/vectordrawable" &gt;
+    &lt;target
+        android:name="rotationGroup"
+        android:animation="@anim/rotation" /&gt;
+&lt;/animated-vector&gt;
+</pre>
+</dd>
+
+<dt><code>res/drawable/vectordrawable.xml</code></dt>
+<dd>
+<pre class="stx">
+&lt;?xml version="1.0" encoding="utf-8"?&gt;
+&lt;vector xmlns:android="http://schemas.android.com/apk/res/android"
+    android:height="64dp"
+    android:width="64dp"
+    android:viewportHeight="600"
+    android:viewportWidth="600" &gt;
+
   &lt;group
+        android:name="rotationGroup"
+        android:pivotX="300.0"
+        android:pivotY="300.0"
+        android:rotation="45.0" &gt;
+        &lt;path
+            android:fillColor="#000000"
+            android:pathData="M300,70 l 0,-70 70,70 0,0 -70,70z" /&gt;
+
   &lt;/group&gt;
+&lt;/vector&gt;
+</pre>
+</dd>
+
+<dt><code>res/anim/rotation.xml</code></dt>
+<dd>
+<pre class="stx">
+&lt;?xml version="1.0" encoding="utf-8"?&gt;
+&lt;objectAnimator xmlns:android="http://schemas.android.com/apk/android"
+    android:duration="6000"
+    android:propertyName="rotation"
+    android:valueFrom="0"
+
   android:valueTo="360" /&gt;
+</pre>
+</dd>
+
+</dl>
+
+<p>There are a lot of files here just to make a single animated vector drawable!
+If the vector drawable and animations are re-used elsewhere, this is the best way to implement an
+animated vector drawable. If they’re only ever used for this animated vector drawable, then there is
+a more compact way to implement them.</p>
+
+<p>Using AAPT’s inline resource format, you can define all three resources in the same XML file.
+Since we’re making an animated vector drawable, we put the file under <code>res/drawable/</code>.</p>
+
+<dl>
+
+<dt><code>res/drawable/avd.xml</code></dt>
+<dd>
+<pre class="stx">
+&lt;?xml version="1.0" encoding="utf-8"?&gt;
+&lt;animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
+    <strong>xmlns:aapt="http://schemas.android.com/aapt"</strong> &gt;
+
+    <strong>&lt;aapt:attr name="android:drawable" &gt;</strong>
+        &lt;vector
+            android:height="64dp"
+            android:width="64dp"
+            android:viewportHeight="600"
+            android:viewportWidth="600" &gt;
+
           &lt;group
+                android:name="rotationGroup"
+                android:pivotX="300.0"
+                android:pivotY="300.0"
+                android:rotation="45.0" &gt;
+                &lt;path
+                    android:fillColor="#000000"
+                    android:pathData="M300,70 l 0,-70 70,70 0,0 -70,70z" /&gt;
+
           &lt;/group&gt;
+        &lt;/vector&gt;
+    <strong>&lt;aapt:attr /&gt;</strong>
+
+    &lt;target
+        android:name="rotationGroup" /&gt;
+        <strong>&lt;aapt:attr name="android:animation" &gt;</strong>
+            &lt;objectAnimator
+                android:duration="6000"
+                android:propertyName="rotation"
+                android:valueFrom="0"
+
               android:valueTo="360" /&gt;
+        <strong>&lt;aapt:attr&gt;</strong>
+&lt;/animated-vector&gt;
+</pre>
+</dd>
+
+</dl>
+
+<p>The XML tag <code>&lt;aapt:attr &gt;</code> tells AAPT that the tag’s child shall be treated as a
+resource and extracted into its own resource file. The value in the attribute name specifies where
+to use the inline resource within the parent tag.</p>
+
+<p>AAPT will generate resource files and names for all of the inline resources.
+Applications built using this inline format are compatible with all versions of Android.</p>
+
diff --git a/docs/html/guide/topics/resources/overview.jd b/docs/html/guide/topics/resources/overview.jd
index c3bd0bf..c496797 100644
--- a/docs/html/guide/topics/resources/overview.jd
+++ b/docs/html/guide/topics/resources/overview.jd
@@ -9,6 +9,7 @@
     <li><a href="accessing-resources.html">Accessing Resources</a></li>
     <li><a href="runtime-changes.html">Handling Runtime Changes</a></li>
     <li><a href="localization.html">Localization</a></li>
+    <li><a href="complex-xml-resources.html">Complex XML Resources</a></li>
   </ol>
 
   <h2>Reference</h2>
@@ -79,6 +80,9 @@
   <dd>A bottom-up guide to localizing your application using alternative resources. While this is
 just one specific use of alternative resources, it is very important in order to reach more
 users.</dd>
+  <dt><strong><a href="complex-xml-resources.html">Complex XML Resources</a></strong></dt>
+  <dd>An XML format for building complex resources like animated vector drawables in a single
+XML file.</dd>
   <dt><strong><a href="available-resources.html">Resource Types</a></strong></dt>
   <dd>A reference of various resource types you can provide, describing their XML elements,
 attributes, and syntax. For example, this reference shows you how to create a resource for
diff --git a/docs/html/images/tools/am-androidmon2.png b/docs/html/images/tools/am-androidmon2.png
new file mode 100644
index 0000000..a4a7571
--- /dev/null
+++ b/docs/html/images/tools/am-androidmon2.png
Binary files differ
diff --git a/docs/html/images/tools/am-cpumon2.png b/docs/html/images/tools/am-cpumon2.png
new file mode 100644
index 0000000..6ac6e02
--- /dev/null
+++ b/docs/html/images/tools/am-cpumon2.png
Binary files differ
diff --git a/docs/html/images/tools/am-dumpalloc2.png b/docs/html/images/tools/am-dumpalloc2.png
new file mode 100644
index 0000000..d936aa8
--- /dev/null
+++ b/docs/html/images/tools/am-dumpalloc2.png
Binary files differ
diff --git a/docs/html/images/tools/am-gc2.png b/docs/html/images/tools/am-gc2.png
new file mode 100644
index 0000000..a5e8b6e
--- /dev/null
+++ b/docs/html/images/tools/am-gc2.png
Binary files differ
diff --git a/docs/html/images/tools/am-gpumon2.png b/docs/html/images/tools/am-gpumon2.png
new file mode 100644
index 0000000..5cf51d9
--- /dev/null
+++ b/docs/html/images/tools/am-gpumon2.png
Binary files differ
diff --git a/docs/html/images/tools/am-icaptures.png b/docs/html/images/tools/am-icaptures.png
new file mode 100644
index 0000000..cf288d6
--- /dev/null
+++ b/docs/html/images/tools/am-icaptures.png
Binary files differ
diff --git a/docs/html/images/tools/am-igraphic.png b/docs/html/images/tools/am-igraphic.png
new file mode 100644
index 0000000..a3c43fa
--- /dev/null
+++ b/docs/html/images/tools/am-igraphic.png
Binary files differ
diff --git a/docs/html/images/tools/am-imaximize.png b/docs/html/images/tools/am-imaximize.png
new file mode 100644
index 0000000..38a6c6c
--- /dev/null
+++ b/docs/html/images/tools/am-imaximize.png
Binary files differ
diff --git a/docs/html/images/tools/am-imaxlogcat.png b/docs/html/images/tools/am-imaxlogcat.png
new file mode 100644
index 0000000..4522bd4
--- /dev/null
+++ b/docs/html/images/tools/am-imaxlogcat.png
Binary files differ
diff --git a/docs/html/images/tools/am-iminimize.png b/docs/html/images/tools/am-iminimize.png
new file mode 100644
index 0000000..d0bbe4c
--- /dev/null
+++ b/docs/html/images/tools/am-iminimize.png
Binary files differ
diff --git a/docs/html/images/tools/am-imovedown.png b/docs/html/images/tools/am-imovedown.png
new file mode 100644
index 0000000..802c13b
--- /dev/null
+++ b/docs/html/images/tools/am-imovedown.png
Binary files differ
diff --git a/docs/html/images/tools/am-imoveup.png b/docs/html/images/tools/am-imoveup.png
new file mode 100644
index 0000000..95f6ef3
--- /dev/null
+++ b/docs/html/images/tools/am-imoveup.png
Binary files differ
diff --git a/docs/html/images/tools/am-logcatmon2.png b/docs/html/images/tools/am-logcatmon2.png
new file mode 100644
index 0000000..5635935
--- /dev/null
+++ b/docs/html/images/tools/am-logcatmon2.png
Binary files differ
diff --git a/docs/html/images/tools/am-networkmon.png b/docs/html/images/tools/am-networkmon.png
index 95b3a5b..f55f853 100644
--- a/docs/html/images/tools/am-networkmon.png
+++ b/docs/html/images/tools/am-networkmon.png
Binary files differ
diff --git a/docs/html/images/tools/am-networkmon2.png b/docs/html/images/tools/am-networkmon2.png
new file mode 100644
index 0000000..d05fcd4
--- /dev/null
+++ b/docs/html/images/tools/am-networkmon2.png
Binary files differ
diff --git a/docs/html/images/tools/am-screenshot.png b/docs/html/images/tools/am-screenshot.png
new file mode 100644
index 0000000..5c27617
--- /dev/null
+++ b/docs/html/images/tools/am-screenshot.png
Binary files differ
diff --git a/docs/html/images/tools/am-sysinfo.png b/docs/html/images/tools/am-sysinfo.png
new file mode 100644
index 0000000..9b5cd17
--- /dev/null
+++ b/docs/html/images/tools/am-sysinfo.png
Binary files differ
diff --git a/docs/html/images/tools/am-video.png b/docs/html/images/tools/am-video.png
new file mode 100644
index 0000000..9787ef8
--- /dev/null
+++ b/docs/html/images/tools/am-video.png
Binary files differ
diff --git a/docs/html/images/tools/support-library/appbar-kitkat.png b/docs/html/images/tools/support-library/appbar-kitkat.png
new file mode 100644
index 0000000..c89fd87
--- /dev/null
+++ b/docs/html/images/tools/support-library/appbar-kitkat.png
Binary files differ
diff --git a/docs/html/images/tools/support-library/appbar-kitkat_2x.png b/docs/html/images/tools/support-library/appbar-kitkat_2x.png
new file mode 100644
index 0000000..c9718e6
--- /dev/null
+++ b/docs/html/images/tools/support-library/appbar-kitkat_2x.png
Binary files differ
diff --git a/docs/html/jd_collections.js b/docs/html/jd_collections.js
index 48c923d..ecd374b 100644
--- a/docs/html/jd_collections.js
+++ b/docs/html/jd_collections.js
@@ -1699,6 +1699,37 @@
       "https://www.youtube.com/watch?v=j3QC6hcpy90"
     ]
   },
+"tools/help/log": {
+    "title": "",
+    "resources": [
+       "tools/help/am-logcat.html"
+    ]
+  },
+"tools/help/monitor": {
+    "title": "",
+    "resources": [
+       "tools/help/am-memory.html",
+       "tools/help/am-cpu.html",
+       "tools/help/am-gpu.html",
+       "tools/help/am-network.html"
+    ]
+  },
+ "tools/help/data": {
+    "title": "",
+    "resources": [
+       "tools/help/am-hprof.html",
+       "tools/help/am-allocation.html",
+       "tools/help/am-methodtrace.html",
+       "tools/help/am-sysinfo.html"
+    ]
+  },
+  "tools/help/shot": {
+    "title": "",
+    "resources": [
+       "tools/help/am-screenshot.html",
+       "tools/help/am-video.html"
+    ]
+  },
   "tools/performance/rendering": {
     "title": "",
     "resources": [
diff --git a/docs/html/jd_extras_en.js b/docs/html/jd_extras_en.js
index ad66f79..b1d7efc 100644
--- a/docs/html/jd_extras_en.js
+++ b/docs/html/jd_extras_en.js
@@ -4456,6 +4456,14 @@
       "https://support.google.com/googleplay/answer/2651410"
     ]
   },
+  "go/libraries": {
+    "title": "",
+    "resources": [
+      "go/libraries/support-library/index.html",
+      "go/libraries/testing-support-library/index.html",
+      "go/libraries/data-binding/index.html"
+    ]
+  },
   "autolanding": {
     "title": "",
     "resources": [
diff --git a/docs/html/ndk/guides/_book.yaml b/docs/html/ndk/guides/_book.yaml
index fdcfe46..287a92d 100644
--- a/docs/html/ndk/guides/_book.yaml
+++ b/docs/html/ndk/guides/_book.yaml
@@ -61,5 +61,14 @@
   - title: OpenSL ES for Android
     path: /ndk/guides/audio/opensl-for-android.html
 
-- title: Graphics
+- title: Vulkan
   path: /ndk/guides/graphics/index.html
+  section:
+  - title: Getting Started
+    path: /ndk/guides/graphics/getting-started.html
+  - title: Design Guidelines
+    path: /ndk/guides/graphics/design-notes.html
+  - title: Shader Compilers
+    path: /ndk/guides/graphics/shader-compilers.html
+  - title: Validation Layers
+    path: /ndk/guides/graphics/validation-layer.html
diff --git a/docs/html/preview/_book.yaml b/docs/html/preview/_book.yaml
index 9f53866..cac6d13 100644
--- a/docs/html/preview/_book.yaml
+++ b/docs/html/preview/_book.yaml
@@ -1,96 +1,342 @@
 toc:
 - title: Program Overview
   path: /preview/overview.html
-  custom_link_attributes:
-  - es-lang="Información general del programa"
-  - ja-lang="プログラム概要"
-  - ko-lang="프로그램 개요"
-  - pt-br-lang="Visão geral do programa"
-  - ru-lang="Обзор программы"
-  - zh-cn-lang="计划概览"
-  - zh-tw-lang="程式總覽"
+  path_attributes:
+  - name: es-lang
+    value: Información general del programa
+  - name: in-lang
+    value: Ikhtisar Program
+  - name: ja-lang
+    value: プログラム概要
+  - name: ko-lang
+    value: 프로그램 개요
+  - name: pt-br-lang
+    value: Visão geral do programa
+  - name: ru-lang
+    value: Обзор программы
+  - name: vi-lang
+    value: Tổng quan về Chương trình
+  - name: zh-cn-lang
+    value: 计划概览
+  - name: zh-tw-lang
+    value: 程式總覽
 
 - title: Support and Release Notes
   path: /preview/support.html
 
 - title: Set Up to Develop
   path: /preview/setup-sdk.html
-  custom_link_attributes:
-  - es-lang="Configurar el SDK de la versión preliminar"
-  - ja-lang="Preview SDK のセットアップ"
-  - ko-lang="미리 보기 SDK 설정하기"
-  - pt-br-lang="Configuração do Preview SDK"
-  - ru-lang="Настройка пакета SDK Preview"
-  - zh-cn-lang="设置预览版 SDK"
-  - zh-tw-lang="設定預覽版 SDK"
+  path_attributes:
+  - name: es-lang
+    value: Configurar el SDK de la versión preliminar
+  - name: in-lang
+    value: Menyiapkan Preview
+  - name: ja-lang
+    value: Preview SDK のセットアップ
+  - name: ko-lang
+    value: 미리 보기 SDK 설정하기
+  - name: pt-br-lang
+    value: Configuração do Preview SDK
+  - name: ru-lang
+    value: Настройка пакета SDK Preview
+  - name: vi-lang
+    value: Kiểm thử trên Thiết bị
+  - name: zh-cn-lang
+    value: 设置预览版 SDK
+  - name: zh-tw-lang
+    value: 設定預覽版 SDK
 
 - title: Test on a Device
   path: /preview/download.html
+  path_attributes:
+  - name: es-lang
+    value: Pruebe en un dispositivo
+  - name: in-lang
+    value: Menguji pada Perangkat
+  - name: ja-lang
+    value: デバイス上でテストする
+  - name: ko-lang
+    value: 기기에서 테스트
+  - name: pt-br-lang
+    value: Testar em um dispositivo
+  - name: ru-lang
+    value: Тестирование на устройстве
+  - name: vi-lang
+    value: Kiểm thử trên Thiết bị
+  - name: zh-cn-lang
+    value: 在设备上测试
+  - name: zh-tw-lang
+    value: 在裝置上測試
 
 - title: Behavior Changes
   path: /preview/behavior-changes.html
-  custom_link_attributes:
-  - es-lang="Cambios en los comportamientos"
-  - ja-lang="動作の変更点"
-  - ko-lang="동작 변경"
-  - pt-br-lang="Mudanças de comportamento"
-  - ru-lang="Изменения в работе"
-  - zh-cn-lang="行为变更"
-  - zh-tw-lang="行為變更"
+  path_attributes:
+  - name: es-lang
+    value: Cambios en los comportamientos
+  - name: in-lang
+    value: Perubahan Perilaku
+  - name: ja-lang
+    value: 動作の変更点
+  - name: ko-lang
+    value: 동작 변경
+  - name: pt-br-lang
+    value: Mudanças de comportamento
+  - name: ru-lang
+    value: Изменения в работе
+  - name: vi-lang
+    value: Các thay đổi Hành vi
+  - name: zh-cn-lang
+    value: 行为变更
+  - name: zh-tw-lang
+    value: 行為變更
   section:
   - title: Background Optimizations
     path: /preview/features/background-optimization.html
+    path_attributes:
+    - name: es-lang
+      value: Optimizaciones en segundo plano
+    - name: in-lang
+      value: Optimisasi Latar Belakang
+    - name: ja-lang
+      value: バックグラウンド処理の最適化
+    - name: ko-lang
+      value: 백그라운드 최적화
+    - name: pt-br-lang
+      value: Otimizações em segundo plano
+    - name: ru-lang
+      value: Оптимизация фоновых процессов
+    - name: vi-lang
+      value: Tối ưu hóa Chạy ngầm
+    - name: zh-cn-lang
+      value: 后台优化
+    - name: zh-tw-lang
+      value: 背景最佳化
   - title: Language and Locale
     path: /preview/features/multilingual-support.html
+    path_attributes:
+    - name: es-lang
+      value: Idioma y configuración regional
+    - name: in-lang
+      value: Bahasa dan Lokal
+    - name: ja-lang
+      value: 言語とロケール
+    - name: ko-lang
+      value: 언어 및 로케일
+    - name: pt-br-lang
+      value: Idioma e localidade
+    - name: ru-lang
+      value: Язык и языковой стандарт
+    - name: vi-lang
+      value: Ngôn ngữ và Bản địa
+    - name: zh-cn-lang
+      value: 语言和区域设置
+    - name: zh-tw-lang
+      value: 語言和地區設定
 
 - title: Android N for Developers
   path: /preview/api-overview.html
-  custom_link_attributes:
-  - es-lang="Información general de la API"
-  - ja-lang="API の概要"
-  - ko-lang="API 개요"
-  - pt-br-lang="Visão geral da API"
-  - ru-lang="Обзор API-интерфейсов"
-  - zh-cn-lang="API 概览"
-  - zh-tw-lang="API 總覽"
+  path_attributes:
+  - name: es-lang
+    value: Información general de la API
+  - name: in-lang
+    value: Android N untuk Pengembang
+  - name: ja-lang
+    value: API の概要
+  - name: ko-lang
+    value: API 개요
+  - name: pt-br-lang
+    value: Visão geral da API
+  - name: ru-lang
+    value: Обзор API-интерфейсов
+  - name: vi-lang
+    value: Android N cho Nhà phát triển
+  - name: zh-cn-lang
+    value: API 概览
+  - name: zh-tw-lang
+    value: API 總覽
   section:
   - title: Multi-Window Support
     path: /preview/features/multi-window.html
+    path_attributes:
+    - name: es-lang
+      value: Compatibilidad con ventanas múltiples
+    - name: in-lang
+      value: Dukungan Multi-Jendela
+    - name: ja-lang
+      value: マルチ ウィンドウのサポート
+    - name: ko-lang
+      value: 다중 창 지원
+    - name: pt-br-lang
+      value: Suporte a várias janelas
+    - name: ru-lang
+      value: Поддержка многооконного режима
+    - name: vi-lang
+      value: Hỗ trợ đa cửa sổ
+    - name: zh-cn-lang
+      value: 多窗口支持
+    - name: zh-tw-lang
+      value: 多視窗支援
   - title: Notifications
     path: /preview/features/notification-updates.html
+    path_attributes:
+    - name: es-lang
+      value: Notificaciones
+    - name: in-lang
+      value: Pemberitahuan
+    - name: ja-lang
+      value: 通知
+    - name: ko-lang
+      value: 알림
+    - name: pt-br-lang
+      value: Notificações
+    - name: ru-lang
+      value: Уведомления
+    - name: vi-lang
+      value: Thông báo
+    - name: zh-cn-lang
+      value: 通知
+    - name: zh-tw-lang
+      value: 通知
   - title: Data Saver
     path: /preview/features/data-saver.html
   - title: TV Recording
     path: /preview/features/tv-recording-api.html
+    path_attributes:
+    - name: es-lang
+      value: Grabación de TV
+    - name: in-lang
+      value: Perekaman TV
+    - name: ja-lang
+      value: TV の録画
+    - name: ko-lang
+      value: TV 녹화
+    - name: pt-br-lang
+      value: Gravação para TV
+    - name: ru-lang
+      value: Запись ТВ
+    - name: vi-lang
+      value: Ghi lại TV
+    - name: zh-cn-lang
+      value: TV 录制
+    - name: zh-tw-lang
+      value: 電視錄製
   - title: Network Security Configuration
     path: /preview/features/security-config.html
+    path_attributes:
+    - name: es-lang
+      value: Configuración de seguridad de la red
+    - name: ja-lang
+      value: ネットワーク セキュリティ構成
+    - name: ko-lang
+      value: 네트워크 보안 구성
+    - name: pt-br-lang
+      value: Configurações de segurança de rede
+    - name: ru-lang
+      value: Конфигурация сетевой безопасности
+    - name: vi-lang
+      value: Cấu hình Bảo mật mạng
+    - name: zh-cn-lang
+      value: 网络安全配置
+    - name: zh-tw-lang
+      value: 網路安全性設定
   - title: ICU4J Support
     path: /preview/features/icu4j-framework.html
+    path_attributes:
+    - name: es-lang
+      value: API de ICU4J del framework de Android
+    - name: in-lang
+      value: ICU4J Android Framework API
+    - name: ja-lang
+      value: ICU4J Android フレームワーク API
+    - name: ko-lang
+      value: ICU4J Android 프레임워크 API
+    - name: pt-br-lang
+      value: APIs de estrutura do Android para ICU4J
+    - name: ru-lang
+      value: API-интерфейсы ICU4J в платформе Android
+    - name: vi-lang
+      value: API Khuôn khổ Android ICU4J
+    - name: zh-cn-lang
+      value: ICU4J Android 框架 API
+    - name: zh-tw-lang
+      value: ICU4J Android 架構 API
   - title: Java 8 Language Features
     path: /preview/j8-jack.html
+    path_attributes:
+    - name: es-lang
+      value: Funciones del lenguaje Java 8
+    - name: in-lang
+      value: Fitur Bahasa Java 8
+    - name: ja-lang
+      value: Java 8 の機能
+    - name: ko-lang
+      value: Java 8 언어 기능
+    - name: pt-br-lang
+      value: Recursos de linguagem do Java 8
+    - name: ru-lang
+      value: Возможности языка Java 8
+    - name: vi-lang
+      value: Tính năng của Ngôn ngữ Java 8
+    - name: zh-cn-lang
+      value: Java 8 语言功能
+    - name: zh-tw-lang
+      value: Java 8 語言功能
   - title: Android for Work Updates
     path: /preview/features/afw.html
   - title: Scoped Directory Access
     path: /preview/features/scoped-folder-access.html
+    path_attributes:
+    - name: es-lang
+      value: Acceso a directorios determinados
+    - name: ja-lang
+      value: 特定のディレクトリへのアクセス
+    - name: ko-lang
+      value: 범위가 지정된 디렉터리 액세스
+    - name: pt-br-lang
+      value: Acesso a diretórios com escopo
+    - name: ru-lang
+      value: Доступ к выделенным каталогам
+    - name: vi-lang
+      value: Truy cập Thư mục theo Phạm vi
+    - name: zh-cn-lang
+      value: 作用域目录访问
+    - name: zh-tw-lang
+      value: 限定範圍目錄存取
 
 - title: Samples
   path: /preview/samples.html
-  custom_link_attributes:
-  - es-lang="Ejemplos"
-  - ja-lang="サンプル"
-  - ko-lang="샘플"
-  - pt-br-lang="Exemplos"
-  - ru-lang="Примеры"
-  - zh-cn-lang="示例"
-  - zh-tw-lang="範例"
+  path_attributes:
+  - name: es-lang
+    value: Ejemplos
+  - name: in-lang
+    value: Contoh
+  - name: ja-lang
+    value: サンプル
+  - name: ko-lang
+    value: 샘플
+  - name: pt-br-lang
+    value: Exemplos
+  - name: ru-lang
+    value: Примеры
+  - name: zh-cn-lang
+    value: 示例
+  - name: zh-tw-lang
+    value: 範例
 
 - title: License Agreement
   path: /preview/license.html
-  custom_link_attributes:
-  - es-lang="Contrato de licencia"
-  - ja-lang="使用許諾契約"
-  - ko-lang="라이선스 계약"
-  - pt-br-lang="Contrato de licença"
-  - ru-lang="Лицензионное соглашение"
-  - zh-cn-lang="许可协议"
-  - zh-tw-lang="授權協議"
+  path_attributes:
+  - name: es-lang
+    value: Contrato de licencia
+  - name: ja-lang
+    value: 使用許諾契約
+  - name: ko-lang
+    value: 라이선스 계약
+  - name: pt-br-lang
+    value: Contrato de licença
+  - name: ru-lang
+    value: Лицензионное соглашение
+  - name: zh-cn-lang
+    value: 许可协议
+  - name: zh-tw-lang
+    value: 授權協議
diff --git a/docs/html/preview/download-ota.jd b/docs/html/preview/download-ota.jd
index 55139f1..7e70f57 100644
--- a/docs/html/preview/download-ota.jd
+++ b/docs/html/preview/download-ota.jd
@@ -248,10 +248,9 @@
   <tr id="fugu">
     <td>Nexus Player <br>"fugu"</td>
     <td><a href="#top" onclick="onDownload(this)"
-      >fugu-ota-2665432-f0f8fea4.zip</a><br>
-      <strong>Note:</strong> DP2 version not yet available.<br>
-      MD5: 4403af764b57502d89111fd68ecb7da5<br>
-      SHA-1: f0f8fea49ea3874b751cf67462ecc5d8e039875e
+      >fugu-ota-npc91o-b1d73dd5.zip</a><br>
+      MD5: d7fbccde75e0b6d860102320ea76d58f<br>
+      SHA-1: b1d73dd5a6498fb6c66e022bd0a6c8b6a6a2374b
     </td>
   </tr>
 
diff --git a/docs/html/preview/download.jd b/docs/html/preview/download.jd
index b673fc1..b0f5369 100644
--- a/docs/html/preview/download.jd
+++ b/docs/html/preview/download.jd
@@ -347,10 +347,9 @@
   <tr id="fugu">
     <td>Nexus Player <br>"fugu"</td>
     <td><a href="#top" onclick="onDownload(this)"
-      >fugu-npc56r-preview-7027d5b6.tgz</a><br>
-      <strong>Note:</strong> DP2 version not yet available.<br>
-      MD5: f5d3d8f75836ccfe4c70e8162e498be4<br>
-      SHA-1: 7027d5b662bceda4c80a91a0a14ef0e5a7ba795b
+      >fugu-npc91o-factory-3b8e3f56.tgz</a><br>
+      MD5: b88b70ecbfb80c983c90b97cb243628b<br>
+      SHA-1: 3b8e3f56a4c35b559783c2928e740df2aab8b377
     </td>
   </tr>
 
diff --git a/docs/html/preview/support.jd b/docs/html/preview/support.jd
index 4caa6b2..f0da709 100644
--- a/docs/html/preview/support.jd
+++ b/docs/html/preview/support.jd
@@ -23,7 +23,7 @@
     <div class="col-6of12">
       <p>
         <em>Date: April 2016<br>
-        Builds: NPC91K<br>
+        Builds: NPC91K, NPC91O<br>
         Emulator support: x86 &amp; ARM (32/64-bit)<br>
         Google Play services: 8.4</em>
       </p>
@@ -325,7 +325,7 @@
   </dt>
 
   <dd>
-    Playback of Netflix HD content is known to fail on Nexus Player.
+    Playback of Netflix HD content may fail on Nexus Player.
   </dd>
 
   <dd>
diff --git a/docs/html/tools/_book.yaml b/docs/html/tools/_book.yaml
index 5395cc8..fb257f3 100644
--- a/docs/html/tools/_book.yaml
+++ b/docs/html/tools/_book.yaml
@@ -2,10 +2,8 @@
 - title: Download
   path: /sdk/index.html
   section:
-  - title: Installing the SDK
+  - title: Install Android Studio
     path: /sdk/installing/index.html
-  - title: Adding SDK Packages
-    path: /sdk/installing/adding-packages.html
 
 - title: Workflow
   path: /tools/workflow/index.html
@@ -27,13 +25,15 @@
     path: /tools/debugging/index.html
   - title: Publishing
     path: /tools/publishing/publishing_overview.html
-    custom_link_attributes:
-    - zh-cn-lang="发布概述"
+    path_attributes:
+    - name: zh-cn-lang
+      value: 发布概述
     section:
     - title: Preparing for Release
       path: /tools/publishing/preparing.html
-      custom_link_attributes:
-      - zh-cn-lang="准备发布"
+      path_attributes:
+      - name: zh-cn-lang
+        value: 准备发布
     - title: Versioning Your Apps
       path: /tools/publishing/versioning.html
     - title: Signing Your Apps
@@ -65,7 +65,9 @@
       path: /tools/debugging/improving-w-lint.html
     - title: Improving Code Inspection with Annotations
       path: /tools/debugging/annotations.html
-    - title: Deep Link and App Indexing API Support
+    - title: Shrink Your Code and Resources
+      path: /tools/help/proguard.html
+    - title: Supporting URLs and App Indexing in Android Studio
       path: /tools/help/app-link-indexing.html
   - title: UI Tools
     path: /tools/studio/ui-tools.html
@@ -82,6 +84,11 @@
       path: /tools/help/image-asset-studio.html
   - title: AVD Manager
     path: /tools/devices/managing-avds.html
+  - title: Android Emulator
+    path: /tools/devices/emulator.html
+    section:
+    - title: Android Emulator Command-Line Features
+      path: /tools/help/emulator.html
   - title: Debugging Tools
     path: /tools/debugging/debugging-studio.html
     section:
@@ -152,15 +159,8 @@
       path: /tools/debugging/debugging-log.html
   - title: mksdcard
     path: /tools/help/mksdcard.html
-  - title: ProGuard
-    path: /tools/help/proguard.html
   - title: Tracer for OpenGL ES
     path: /tools/help/gltracer.html
-  - title: Virtual Device Emulator
-    path: /tools/devices/emulator.html
-    section:
-    - title: Command Reference
-      path: /tools/help/emulator.html
   - title: zipalign
     path: /tools/help/zipalign.html
 
diff --git a/docs/html/tools/help/am-allocation.jd b/docs/html/tools/help/am-allocation.jd
new file mode 100644
index 0000000..20570c3
--- /dev/null
+++ b/docs/html/tools/help/am-allocation.jd
@@ -0,0 +1,220 @@
+page.title=Allocation Tracker
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Memory Monitor to capture allocation data about your app. The Allocation Tracker displays each method responsible for an allocation, as well as the allocation size and number of instances.
+page.image=tools/help/thumbnails/am_alloctracker.png
+page.article=true
+
+@jd:body
+
+<div id="qv-wrapper">
+<div id="qv">
+  <h2>In this document</h2>
+<ol>
+      <li><a href="#display">Understanding the Allocation Tracker Display</a></li>
+      <li><a href="#alloc-snapshot">Taking and Displaying a Snapshot of Allocation Data</a></li>
+      <li><a href="#alloc-viewing">Viewing a Saved Allocation Tracking File</a></li>
+      <li><a href="#alloc-sorting">Sorting Allocation Data</a></li>
+      <li><a href="#alloc-source">Displaying Java Source</a></li>
+      <li><a href="#alloc-files">Working with Allocation Tracking Files</a></li>
+</ol>
+
+ <h2>See also</h2>
+  <ol>
+    <li><a href="{@docRoot}training/articles/memory.html">Managing Your App's Memory</a></li>
+    <li><a href="{@docRoot}guide/practices/verifying-apps-art.html#GC_Migration">Addressing Garbage Collection Issues</a></li>
+    <li><a href="{@docRoot}tools/debugging/debugging-memory.html">Investigating Your RAM Usage</a></li>
+  </ol>
+
+</div>
+</div>
+
+
+
+
+<p>Android Studio allows you to track memory allocation as it monitors memory use. Tracking memory
+  allocation allows you to monitor where objects are being allocated when you perform certain
+  actions. Knowing these allocations enables you to adjust the method calls related to those actions
+  to optimize app performance and memory use.</p>
+
+<p>The Allocation Tracker does the following:</p>
+<ul>
+<li>Shows when and where your code allocates object types, their size, allocating thread, and stack
+  traces.</li>
+<li>Helps recognize memory churn through recurring allocation/deallocation patterns.</li>
+<li>Helps you track down memory leaks when used in combination with the HPROF Viewer. For example,
+  if you see a bitmap object resident on the heap, you can find its allocation location with
+  Allocation Tracker.</li>
+</ul>
+
+
+<p>However, it takes time and experience to learn to interpret the output from this tool.</p>
+
+<h2 id="display">
+  Understanding the Allocation Tracker Display
+</h2>
+
+<p>
+  The Allocation Tracker looks similar to the following figure:
+</p>
+<img src="{@docRoot}images/tools/am-alloctracker.png" />
+<p>
+
+
+<p>The tool displays the following information: </p>
+
+<table>
+  <tr>
+    <th scope="col">Column</th>
+    <th scope="col">Description</th>
+  </tr>
+
+  <tr>
+    <td><strong>Method</strong></td>
+    <td>The Java method responsible for the allocation.</td>
+  </tr>
+  <tr>
+    <td><strong>Count</strong></td>
+    <td>Total number of instances allocated.</td>
+  </tr>
+  <tr>
+    <td><strong>Size</strong></td>
+    <td>The total amount of allocated memory in bytes.</td>
+  </tr>
+
+</table>
+
+<h2 id="alloc-snapshot">Taking and Displaying a Snapshot of Allocation Data</h2>
+
+<p>To examine allocation data:</p>
+<ol>
+  <li><a href="{@docRoot}tools/help/am-memory.html#displaying">Display a running app in the Memory
+    Monitor</a>.</li>
+<li>Click Start Allocation Tracking
+  <img src="{@docRoot}images/tools/am-ialloctracking.png"
+  style="vertical-align:sub;margin:0;height:17px" alt="Start Allocation Tracking icon" />. </li>
+<li>Click Start Allocation Tracking
+  <img src="{@docRoot}images/tools/am-ialloctracking.png"
+  style="vertical-align:sub;margin:0;height:17px" alt="Start Allocation Tracking icon" /> again to
+  deselect it and end the snapshot. </li>
+
+  <p>The Memory Monitor displays the period when it took the snapshot. In the following
+    figure, you can see the snapshot period, as shown on the left. By comparison, when you dump the
+    Java heap, the Memory Monitor displays just the point where the heap snapshot was taken, as
+    shown on the right.</p>
+    <img src="{@docRoot}images/tools/am-dumpalloc2.png" />
+
+<p>Android Studio creates the heap snapshot file with the
+  filename <code><em>package_yyyy.mm.dd_hh.mm.ss</em>.alloc</code> using the activity package (or
+  project) name, year, month, day,
+  hour, minute, and second of the capture, for example,
+  <code>com.android.calc_2015.11.17_14.58.48.alloc</code>.</p>
+
+  The Allocation Tracker appears.
+</p>
+
+<li>Optionally click the graphic icon <img src="{@docRoot}images/tools/am-igraphic.png"
+style="vertical-align:sub;margin:0;height:17px"
+  alt="graphic icon" /> to display a visual representation of the data.
+  </li>
+
+
+
+
+<li>Select the Group By menu option you want to display: </li>
+<ul>
+<li><strong>Group by Allocator</strong> </li>
+<li><strong>Group by Method</strong></li>
+</ul>
+
+</ol>
+
+
+<h2 id="alloc-viewing">Viewing a Saved Allocation Tracking File</h2>
+<p>After you capture allocation data, Android Studio automatically stores it so
+you can view it again.</p>
+<p>To view an allocation tracking file in the Allocation Tracker:</p>
+
+
+<ol>
+<li>Click
+<img src="{@docRoot}images/tools/am-icaptures.png"
+style="vertical-align:sub;margin:0;height:17px"
+  alt="Captures icon" /> in the main window.</li>
+
+<p>Or select <strong>View</strong> > <strong>Tools Windows</strong> >
+<strong>Captures</strong>.</p>
+<p>The <em>Captures</em> window appears.</p>
+<li>Open the <strong>Allocation Tracking</strong> folder.</li>
+<li>Double-click the file to view it.</li>
+</ol>
+
+<h2 id="alloc-sorting">Sorting Allocation Data</h2>
+
+<p>To sort allocation data:</p>
+<ul>
+<li>In the Allocation Tracker, click a column heading to sort the table by ascending or
+  descending order. </li>
+</ul>
+
+
+<h2 id="alloc-source">Displaying Java Source</h2>
+<p>For some items displayed in the Allocation Tracker, you can view the Java source.</p>
+<p>To display Java source:</p>
+<ul>
+<li>In the Allocation Tracker, right-click a method and then select <strong>Jump to Source</strong>.
+</li>
+<li>In the Allocation Tracker, select a method and then click Jump to Source
+  <img src="{@docRoot}images/tools/am-ijumptosource.png"
+  style="vertical-align:sub;margin:0;height:17px" alt="Jump to Source icon" />. </li>
+</ul>
+
+<p>The source code appears in the Code Editor.</p>
+
+
+<h2 id="alloc-files">Working with Allocation Tracking Files</h2>
+<p>You can rename, locate, and delete an allocation tracking file from within
+Android Studio.</p>
+
+<h3 id="alloc-renaming">Renaming an allocation tracking file</h3>
+
+<p>If you rename a file from within Android Studio, it continues to appear in the <em>Captures</em>
+  window.</p>
+<p>To rename an allocation tracking file:</p>
+<ol>
+<li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>.</li>
+<li>In the <em>Rename</em> dialog, specify the name of the file and click <strong>OK</strong>.</li>
+</ol>
+
+
+<h3 id="alloc-locating">Locating an allocation tracking file</h3>
+<p>You can quickly discover where Android Studio stored allocation tracking files on disk.</p>
+
+
+<p>To locate an allocation tracking file from Android Studio: </p>
+<ul>
+<li>In the <em>Captures</em> window, right-click allocation file and select
+  <strong>Show</strong> or <strong>Reveal</strong>.</li>
+
+<p>Android Studio opens an operating system file browser displaying the location where the file
+  resides.</p>
+</ul>
+
+<p class="note"><strong>Note:</strong> If you move an allocation tracking file, Android Studio
+  no longer displays it in the <em>Captures</em> window. To display the file, use
+  <strong>File</strong>
+  &gt; <strong>Open</strong>. Also, rename the file from the <em>Captures</em>
+  window and not in the operating system file browser. </p>
+
+<h3 id="alloc-deleting">Deleting an allocation tracking file</h3>
+
+
+<p>To delete an allocation tracking file: </p>
+<ul>
+<li>In the <em>Captures</em> window, right-click an allocation tracking file and select
+  <strong>Delete</strong>.</li>
+
+<p>Android Studio deletes the file from the <em>Captures</em> dialog and from disk. </p>
+</ul>
diff --git a/docs/html/tools/help/am-basics.jd b/docs/html/tools/help/am-basics.jd
new file mode 100644
index 0000000..4bacecf
--- /dev/null
+++ b/docs/html/tools/help/am-basics.jd
@@ -0,0 +1,329 @@
+page.title=Android Monitor Basics
+parent.title=Android Monitor
+parent.link=index.html
+page.tags=monitor
+@jd:body
+
+<div id="qv-wrapper">
+<div id="qv">
+  <h2>In this document</h2>
+<ol>
+  <li><a href="#byb">Prerequisites and Dependencies</a></li>
+  <li><a href="#displaying">Displaying Android Monitor</a></li>
+  <li><a href="#profiling">Profiling a Running App in Android Monitor</a></li>
+  <li><a href="#switching">Switching between Devices and Apps</a></li>
+  <li><a href="#rearranging">Rearranging Android Monitor Windows</a></li>
+  <li><a href="#terminating">Terminating an App</a></li>
+  <li><a href="#removing">Removing an App from a Device</a></li>
+  <li><a href="#other">Using Other Main Window Features</a></li>
+</ol>
+
+
+
+
+
+</div>
+</div>
+
+<p>
+  Android Monitor has a main window that contains the logcat, Memory, CPU, GPU, and Network
+  Monitors. From this window, you can select a device and app process to work with, terminate an
+  app, collect <code>dumpsys</code> system information, and create screenshots and videos of the
+  running app.
+</p>
+
+
+<h2 id="byb">
+   Prerequisites and Dependencies
+</h2>
+
+<p>
+   Before you start using Android Monitor, you need to set up your environment, as well as the
+   hardware device or emulator. All of the monitors require the following:
+</p>
+    <ul>
+      <li>If you want to run your app on a hardware device (as opposed to the emulator), connect it
+        to the USB port. Make sure your development computer
+        <a href="{@docRoot}tools/device.html#setting-up">detects your device</a>, which often
+        happens automatically when you connect it.
+  </li>
+      <li>Enable ADB integration by selecting <strong>Tools</strong> &gt; <strong>Android</strong>
+        &gt; <strong>Enable ADB Integration</strong>. <strong>Enable ADB Integration</strong>
+        should have a check mark next to it in the menu to indicate it's enabled.
+      </li>
+  <li>
+    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
+  </li>
+    </ul>
+
+  <p>
+   All but the logcat Monitor have these additional requirements:
+</p>
+<ul>
+  <li>
+    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
+    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
+    <strong>Developer Options</strong> on the device or emulator.
+  </li>
+
+  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
+  <code>build.gradle</code> file (it’s initially set by default).
+  </li>
+</ul>
+
+
+<p>
+   The GPU Monitor has this requirement as well:
+</p>
+<ul>
+  <li>For Android 5.0 (API level 21) and Android 5.1 (API level 22), in <strong>Developer
+  Options</strong> on the device or emulator, set <strong>Profile GPU rendering</strong> to
+  <strong>In adb shell dumpsys gfxinfo</strong>.
+  </li>
+</ul>
+<p>
+   The Network Monitor and the Video Capture tool work with a hardware device
+   only, not the emulator.
+</p>
+
+
+
+<h2 id="displaying">
+  Displaying Android Monitor
+</h2>
+
+<p>
+  Android Monitor is integrated into the Android Studio main window:
+</p>
+
+<ul>
+  <li>To display Android Monitor, click <img src="{@docRoot}images/tools/am-icon.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Android Monitor icon" />,
+    which by default is at the bottom of the main window.
+  </li>
+
+  <li>To hide Android Monitor, click <img src="{@docRoot}images/tools/am-icon.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Android Monitor icon" /> again.
+  </li>
+  <li>Or select <strong>View</strong> > <strong>Tool Windows</strong> >
+  <strong>Android Monitor</strong>.</li>
+</ul>
+ <p class="note">
+      <strong>Note:</strong> If you don't see the sidebar buttons, you can
+      display them by selecting <strong>View</strong> >
+      <strong>Tool Buttons</strong>.
+    </p>
+<p>
+  Android Monitor looks like the following figure:
+</p>
+<img src="{@docRoot}images/tools/am-androidmon2.png" style="vertical-align:sub;margin:0" />
+
+<h2 id="profiling">
+  Profiling a Running App in Android Monitor
+</h2>
+
+<p>
+  After you've met the prerequisites and optionally connected a hardware device, you're ready
+  to profile an app in Android Monitor:
+</p>
+
+<ol>
+
+  <li>Open an app project and <a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">run the app</a> on a device or
+  emulator.
+  </li>
+
+  <li>Display Android Monitor and click the tab for the monitor you want to view.
+  </li>
+  <li>Follow the instructions about using the monitor:
+  </li>
+    <ul>
+      <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
+      </li>
+
+      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
+      </li>
+
+      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
+      </li>
+
+      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
+      </li>
+
+      <li>
+        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
+      </li>
+    </ul>
+</ol>
+    <h2 id="switching">
+      Switching between Devices and Apps
+    </h2>
+
+    <p>
+      By default, Android Monitor displays data for your most recently run app. You can switch to
+      another device and app as needed. In addition to currently running apps, you can view
+      information about apps that are no longer running so you can continue to see any information
+      about them that you gathered previously.
+    </p>
+
+    <p>
+      At the top of the Android Monitor main window are two menus listing devices and processes. To
+      switch to another device, process, or both:
+    </p>
+
+    <ol>
+      <li>Select the device or emulator.
+      </li>
+
+    <p>
+      The Device menu lists the devices and emulators that are running or have run during your
+      current session. There are various status messages that can appear in the Device menu:
+    </p>
+
+    <ul>
+      <li>
+        <strong>DISCONNECTED</strong> - You closed an emulator or unplugged a device from the
+        computer.
+      </li>
+
+      <li>
+        <strong>UNAUTHORIZED</strong> - A device needs you to accept the incoming computer
+        connection. For example, if the connected device displays an <em>Allow USB Debugging</em>
+        dialog, click <strong>OK</strong> to allow the connection.
+      </li>
+
+      <li>
+        <strong>OFFLINE</strong> - Android Monitor can’t communicate with a device, even though it
+        has detected that device.
+      </li>
+    </ul>
+
+  <li>Select the process.
+  </li>
+  <p>
+  The Process menu lists the processes that are running or have run during your current session. If
+  a process is no longer running, the menu displays a status of <strong>DEAD</strong>.
+</p>
+</ol>
+
+
+
+
+<h2 id="rearranging">
+  Rearranging Android Monitor Windows
+</h2>
+
+<p>
+  You can rearrange the Android Monitor windows for optimal viewing during your
+  tests:
+</p>
+<ul>
+  <li>To move a monitor up or down, click Move Monitor Up
+  <img src="{@docRoot}images/tools/am-imoveup.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Move Monitor Up icon" /> or Move Monitor Down
+    <img src="{@docRoot}images/tools/am-imovedown.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Move Monitor Down icon" />.
+  </li>
+  <li>To minimize or maximize a monitor, click Minimize Monitor
+  <img src="{@docRoot}images/tools/am-iminimize.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Minimize Monitor icon" />
+    or Maximize Monitor
+    <img src="{@docRoot}images/tools/am-imaximize.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Maximize Monitor icon" />.
+  </li>
+</ul>
+
+<p>
+  To rearrange the <strong>logcat</strong> and <strong>Monitors</strong> tabs:
+</p>
+<ul>
+  <li>To reorder the logcat or monitor group, move the tabs back and forth.
+  </li>
+
+  <li>To move the logcat or monitor group to a standalone window, drag a tab
+  to a different location on the screen. Or, select
+  <img src="{@docRoot}images/tools/am-igear.png" style="vertical-align:sub;margin:0;height:17px"
+  alt="Gear menu icon" /> &gt; <strong>Floating Mode</strong>.
+  </li>
+
+
+  <li>To dock a standalone window, drag it to the Android Monitor
+  tab area.</li>
+
+
+  <li>To combine the logcat and monitor group displays together, drag a tab and
+  move it onto another monitor.
+  </li>
+
+  <li>To hide a tab, click the
+    <img src="{@docRoot}images/tools/am-ihide.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Hide icon" /> icon. To make it reappear, click Restore Monitors View
+    <img src="{@docRoot}images/tools/am-imaximize.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Restore Monitors View icon" />
+    or the Restore logcat View
+    <img src="{@docRoot}images/tools/am-imaxlogcat.png" style="vertical-align:sub;margin:0;height:17px"
+    alt="Restore logcat View icon" />
+    on the far right of the row of tabs.
+  </li>
+</ul>
+
+<h2 id="terminating">
+  Terminating an App
+</h2>
+
+<p>
+  To stop an app you’ve run from Android Studio:
+</p>
+
+<ol>
+  <li>
+    <a href="#switching">Select the device and the process</a> in the Android Monitor
+    menus, if needed.
+  </li>
+
+  <li>Click Terminate Application <img src="{@docRoot}images/tools/am-iterminate.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Terminate App icon" />.
+  </li>
+
+
+<p>
+  The process status changes to <strong>DEAD</strong> in the Processes menu. The emulator or device
+  continues to run, but the app closes. Any running monitors in Android Monitor stop.
+</p>
+</ol>
+
+<h2 id="removing">
+  Removing an App from a Device
+</h2>
+
+<p>
+  To remove an app from a device you use for development, use the normal uninstall procedure on the
+  device.
+</p>
+
+<p>
+  If you run a new version of an app from Android Studio that’s been already installed on a
+  hardware device, the device displays an <em>Application Installation Failed</em> dialog. Click
+  <strong>OK</strong> to install the new version of the app.
+</p>
+
+<h2 id="other">
+  Using Other Main Window Features
+</h2>
+<p>
+  From the Android Monitor main window, you can also do the following:
+</p>
+
+<ul>
+  <li>
+    <a href="{@docRoot}tools/help/am-sysinfo.html">Examine <code>dumpsys</code> system information</a>.
+  </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-screenshot.html">Take a screen capture of the device</a>.
+  </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-video.html">Record a video from the screen</a>.
+  </li>
+</ul>
+
diff --git a/docs/html/tools/help/am-cpu.jd b/docs/html/tools/help/am-cpu.jd
index 62b3590..420d6f8 100644
--- a/docs/html/tools/help/am-cpu.jd
+++ b/docs/html/tools/help/am-cpu.jd
@@ -1,7 +1,12 @@
 page.title=CPU Monitor
 parent.title=Android Monitor
 parent.link=android-monitor.html
-page.tags=monitor
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the CPU Monitor to display CPU usage in real time and the percentage of total CPU time (including all cores) used in user and kernel mode.
+page.image=tools/help/thumbnails/am-cpumon.png
+page.article=true
+
 @jd:body
 
 <div id="qv-wrapper">
@@ -9,63 +14,9 @@
   <h2>In this document</h2>
 <ol>
   <li><a href="#running">Displaying a Running App in the CPU Monitor</a></li>
-  <li><a href="#trace">Performing a Method Trace in the CPU Monitor</a></li>
-  <li><a href="#viewtrace">Viewing a Saved Method Trace</a></li>
-  <li><a href="#sorttrace">Sorting Method Trace Data</a></li>
-  <li><a href="#renametrace">Renaming a Method Trace File</a></li>
-  <li><a href="#locatetrace">Locating a Method Trace File on Disk</a></li>
-  <li><a href="#deletetrace">Deleting a Method Trace File</a></li>
+  <li><a href="#snapshot">Recording Call Stack Changes</a></li>
 </ol>
 
- <h2>See also</h2>
-  <ol>
-    <li>
-        <a href="{@docRoot}tools/help/android-monitor.html">Android Monitor</a>
-      </li>
-    <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
-
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
-  </ol>
-
-
-<h2>
-  Dependencies and Prerequisites
-</h2>
-
-<ul>
-  <li>Make sure your development computer detects your hardware device, which often happens
-  automatically when you connect it to a USB port.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
-    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
-    <strong>Developer Options</strong> on the device or emulator.
-  </li>
-
-  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
-  <code>build.gradle</code> file (it’s initially set by default).
-  </li>
-
-<li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-  <strong>Enable ADB Integration</strong>.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-
-</ul>
-
 </div>
 </div>
 
@@ -73,253 +24,66 @@
 <p>
   The CPU Monitor lets you easily monitor the central processing unit (CPU) usage of your app. It
   displays CPU usage in real time and displays the percentage of total CPU time (including all cores)
-  used by user and kernel mode. In user mode, the code must use system APIs to access hardware or
-  memory, and crashes are usually recoverable. In kernel mode, the code can directly access
-  hardware, including memory addresses; crashes halt the device.
+  used in user and kernel mode. In user mode, the code must use system APIs to access hardware or
+  memory, has access to virtual memory addresses only, and crashes are usually
+  recoverable. In kernel mode, the code can directly access
+  hardware, including physical memory addresses; crashes halt the device.
 </p>
 
+
 <h2 id="running">
   Displaying a Running App in the CPU Monitor
 </h2>
 
 <p>
-  Follow these steps:
+  To display an app running on a particular device or emulator in the CPU Monitor:
 </p>
 
 <ol>
-  <li>Optionally connect a hardware device.
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
   </li>
-
-  <li>
-    <a href="{@docRoot}tools/help/android-monitor.html#displaying">Display Android Monitor</a>.
+ <li>Open an app project.
   </li>
-
-  <li>Click the <strong>CPU</strong> tab.
-  </li>
-
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run it</a> on a hardware device or
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on a hardware device or
   emulator.
   </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+  <li>Click the <strong>Monitors</strong> tab and <a href=
+  "{@docRoot}tools/help/am-basics.html#rearranging">display the CPU Monitor</a>.
+  </li>
+
 
   <li>Enable the CPU Monitor by clicking Pause <img src="{@docRoot}images/tools/am-ipause.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect
-  it.
+    style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect it.
   </li>
 
+
 <p>
   The CPU Monitor starts to display any CPU usage.
   In the graph, the y-axis displays the percentage of CPU used. The x-axis records the time elapsed
   and starts with seconds, and then minutes and seconds, and so on.
 </p>
-<img src="{@docRoot}images/tools/am-cpumon.png" style="vertical-align:sub;margin:0;width:450px" />
+<img src="{@docRoot}images/tools/am-cpumon2.png" style="vertical-align:sub;margin:0" />
   <li>To stop the CPU Monitor, click Pause <img src="{@docRoot}images/tools/am-ipause.png"
     style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> again to select
   it.
   </li>
 </ol>
 
-
-<h2 id="trace">
-  Performing a Method Trace in the CPU Monitor
+<h2 id="snapshot">
+  Recording Call Stack Changes
 </h2>
 
 <p>
-  Follow these steps:
-</p>
-
-<ol>
-  <li>
-    <a href="{@docRoot}tools/help/android-monitor.html#displaying">Display a running app in the CPU
-    Monitor</a>.
-  </li>
-
-  <li>Start a trace by clicking Start Method Tracing <img src="{@docRoot}images/tools/am-imethodtrace.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Start Method Tracing icon" /> to
-  select it.
-  </li>
-
-  <li>To stop the trace, click Stop Method Tracing <img src="{@docRoot}images/tools/am-imethodtrace.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Stop Method Tracing icon" /> to
-  deselect it.
-  </li>
-
-<p>
-  The method trace appears in the Code Editor area:
-</p>
-<img src="{@docRoot}images/tools/am-methodtrace.png" alt="Method Trace" />
-<p>
-  Android Studio creates the method trace file
-  with the filename <code>Trace_<em>yyyy.mm.dd_hh.mm.ss</em>.trace</code>
-  using the year, month, day, hour, minute, and second of the capture, for example,
-  <code>Trace_2015.11.17_14.58.48.trace</code>.
-</p>
-  <li>Specify display options:
-    <ul>
-      <li>Select a <strong>Thread</strong>.
-      </li>
-
-      <li>Select an <strong>x-axis</strong> time for the graphic and the method list:
-      </li>
-
-        <ul>
-          <li>
-            <strong>Wall Clock Time</strong> - Total CPU time elapsed between the method call and
-            return.
-          </li>
-
-          <li>
-            <strong>Thread Time</strong> - Total time during which the JRE scheduled the
-            thread during call processing. It’s less than or equal to the Wall Clock Time: less if
-            the JRE interrupted the thread, and equal if it didn’t.
-            The thread might not run continuously; when it’s not executing, that time is excluded.
-            If threads are interrupted often and it’s not by design, the interruptions affect app
-            performance. However, an example of a by-design use is synchronous operations that take
-            a long time, such as file transfers and reads from disk, where the method could be the
-            asynchronous wrapper for the synchronous reader.
-          </li>
-       </ul>
-
-        <li>
-          Optionally select <strong>Color by inclusive time</strong>.
-        </li>
-        </ul>
-
-        <p>
-          The display shows the following information:
-        </p>
-<table>
-  <tr>
-    <th scope="col">Field</th>
-    <th scope="col">Description</th>
-  </tr>
-
-  <tr>
-    <td><strong>Name</strong></td>
-    <td>The name of the method.</td>
-  </tr>
-
-  <tr>
-    <td><strong>Invocation Count</strong></td>
-    <td>How many times the method was called.</td>
-  </tr>
-
-  <tr>
-    <td><strong>Inclusive Time (microseconds)</strong></td>
-    <td>Time spent in the method and all of its children, either wall clock or thread time,
-          depending on your selection in the <strong>x-axis</strong> menu.</td>
-  </tr>
-
-  <tr>
-    <td><strong>Exclusive Time (microseconds)</strong></td>
-    <td>Time spent just in the method (excluding time spent in its children), either wall clock
-          or thread time, depending on your selection in the <strong>x-axis</strong> menu.</td>
-  </tr>
-</table>
-<p class="note"><strong>Note:</strong> Running the method trace significantly affects CPU timings.
-  Use the method trace to understand the flow of the program, but not for performance timings.</p>
-        <p>
-          The graphic represents the wall clock or thread time for each method. Hover the cursor
-          over the display to receive information about the method. This information also appears
-          in the table.
-        </p>
-</ol>
-        <h2 id="viewtrace">
-          Viewing a Saved Method Trace
-        </h2>
-
-        <p>
-          After you do a method trace, Android Studio automatically stores it so you can view it
-          again. To examine the trace, follow these steps:
-        </p>
-
-        <ol>
-          <li>Click <strong>Captures</strong> in the main window.
-          </li>
-
-        <p>
-          The <em>Captures</em> window appears.
-        </p>
-
-      <li>Open the <strong>Methods Tracing</strong> folder.
-      </li>
-
-      <li>Double-click the file to view it.
-      </li>
-</ol>
-
-<h2 id="sorttrace">
-  Sorting Method Trace Data
-</h2>
-
-<p>
-  You can sort the data by method name, count, inclusive time, and exclusive time. Follow this step:
-</p>
-
-
-<ul>
-  <li>Click a column heading to sort the table by ascending or descending order.
-  </li>
-</ul>
-
-<h2 id="renametrace">
-  Renaming a Method Trace File
-</h2>
-
-<p>
-  Rename a method trace file from within Android Studio so it
-  continues to appear in the <em>Captures</em> window. Follow these steps:
-</p>
-
-<ol>
-  <li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>.
-  </li>
-
-  <li>In the dialog, specify the name of the file and click <strong>OK</strong>.
-  </li>
-</ol>
-
-<h2 id="locatetrace">
-  Locating a Method Trace File on Disk
-</h2>
-
-<p>
-  You can quickly discover where Android Studio stored method trace files on disk. Follow this step:
+  You can capture a record of the changes on the call stack during a particular
+  time period while the CPU Monitor is running. For more information, see
+  <a href="{@docRoot}tools/help/am-methodtrace.html">Method Trace</a>.
 </p>
 
 
 
-<ul>
-  <li>In the <em>Captures</em> window, right-click a method trace file and select <strong>Show in
-  files</strong>.
-  </li>
 
-<p>
-  Android Studio opens an operating system file browser displaying the location where the file
-  resides.
-</p>
-</ul>
-<p class="note">
-  <strong>Note:</strong> If you move a method trace file, Android Studio no longer displays the file
-  in the <em>Captures</em> window. To display it, use <strong>File</strong> &gt;
-  <strong>Open</strong>. Also, rename a file from the <em>Captures</em>
-  window and not in the operating system file browser.
-</p>
-
-<h2 id="deletetrace">
-  Deleting a Method Trace File
-</h2>
-
-<p>
-  Follow this step in Android Studio:
-</p>
-
-<ul>
-  <li>In the <em>Captures</em> window, right-click a method trace file and select
-  <strong>Delete</strong>.
-  </li>
-</ul>
-
-<p>
-  Android Studio deletes the file from the <em>Captures</em> dialog and from disk.
-</p>
\ No newline at end of file
diff --git a/docs/html/tools/help/am-gpu.jd b/docs/html/tools/help/am-gpu.jd
index a244b22..fb140ad 100644
--- a/docs/html/tools/help/am-gpu.jd
+++ b/docs/html/tools/help/am-gpu.jd
@@ -1,7 +1,12 @@
 page.title=GPU Monitor
 parent.title=Android Monitor
 parent.link=android-monitor.html
-page.tags=monitor
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the GPU Monitor for a visual representation of how much time it takes to render the frames of a UI window. Use this information to optimize the code that displays graphics and conserve memory.
+page.image=tools/help/thumbnails/am-gpumon.png
+page.article=true
+
 @jd:body
 
 <div id="qv-wrapper">
@@ -11,59 +16,6 @@
   <li><a href="#running">Displaying a Running App in the GPU Monitor</a></li>
 </ol>
 
- <h2>See also</h2>
-  <ol>
-    <li>
-        <a href="{@docRoot}tools/help/android-monitor.html">Android Monitor</a>
-      </li>
-    <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
-
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
-  </ol>
-
-<h2>
-  Dependencies and Prerequisites
-</h2>
-
-<ul>
-  <li>Make sure your development computer detects your hardware device, which often happens
-  automatically when you connect it to a USB port.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
-    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
-    <strong>Developer Options</strong> on the device or emulator.
-  </li>
-
-  <li>For Android 5.0 (API level 21) and Android 5.1 (API level 22), in <strong>Developer
-  Options</strong> on the device or emulator, set <strong>Profile GPU rendering</strong> to
-  <strong>In adb shell dumpsys gfxinfo</strong>.
-  </li>
-
-  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
-  <code>build.gradle</code> file (it’s initially set by default).
-  </li>
-
-
-  <li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-  <strong>Enable ADB Integration</strong>.
-  </li>
-
-   <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-</ul>
-
 </div>
 </div>
 
@@ -96,33 +48,34 @@
 </h2>
 
 <p>
-  Follow these steps:
+  To display an app running on a particular device or emulator in the GPU Monitor:
 </p>
 
 <ol>
-  <li>Optionally connect a hardware device.
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
   </li>
-
-  <li>
-    <a href="{@docRoot}tools/help/android-monitor.html#displaying">Display Android Monitor</a>.
+ <li>Open an app project.
   </li>
-
-  <li>Click the <strong>GPU</strong> tab.
-  </li>
-
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run it</a> on a hardware device or
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on a hardware device or
   emulator.
   </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+  <li>Click the <strong>Monitors</strong> tab and <a href=
+  "{@docRoot}tools/help/am-basics.html#rearranging">display the GPU Monitor</a>.
+  </li>
 
-  <li>Enable the GPU Monitor by clicking Pause <img src="{@docRoot}images/tools/am-ipause.png" style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect
-  it.
+  <li>Enable the GPU Monitor by clicking Pause <img src="{@docRoot}images/tools/am-ipause.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect it.
   </li>
 
   <p>
   Any GPU usage begins to appear in the GPU Monitor:
 </p>
-  <img src="{@docRoot}images/tools/am-gpumon.png" style="vertical-align:sub;margin:0;width:450px" />
+  <img src="{@docRoot}images/tools/am-gpumon2.png" style="vertical-align:sub;margin:0" />
 
 <p>
   The y-axis is the amount of time it takes the GPU to execute, process, prepare, and draw frames,
diff --git a/docs/html/tools/help/am-hprof.jd b/docs/html/tools/help/am-hprof.jd
new file mode 100644
index 0000000..1eef6ab
--- /dev/null
+++ b/docs/html/tools/help/am-hprof.jd
@@ -0,0 +1,355 @@
+page.title=HPROF Viewer and Analyzer
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Memory Monitor to dump the Java heap to an HPROF file. The HPROF Viewer displays classes, instances of each class, and a reference tree to help you track memory usage and find memory leaks.
+page.image=tools/help/thumbnails/am_hprofviewer.png
+page.article=true
+
+@jd:body
+
+<div id="qv-wrapper">
+<div id="qv">
+  <h2>In this document</h2>
+<ol>
+      <li><a href="#why">Why Look at the Java Heap?</a></li>
+      <li><a href="#display">Understanding the HPROF Viewer Display</a></li>
+      <li><a href="#hprof-snapshot">Taking a Snapshot of the Java Heap</a></li>
+      <li><a href="#hprof-viewing">Viewing a Saved HPROF File</a></li>
+      <li><a href="#hprof-diving">Diving into Heap Dump Data in the HPROF Viewer</a></li>
+      <li><a href="#hprof-analyzing">Analyzing Heap Dump Data in the HPROF Analyzer</a></li>
+      <li><a href="#hprof-sorting">Sorting Heap Dump Data</a></li>
+      <li><a href="#hprof-source">Displaying Java Source</a></li>
+      <li><a href="#hprof-files">Working with HPROF Files</a></li>
+
+</ol>
+
+ <h2>See also</h2>
+  <ol>
+    <li><a href="{@docRoot}training/articles/memory.html">Managing Your App's Memory</a></li>
+    <li><a href="{@docRoot}guide/practices/verifying-apps-art.html#GC_Migration">Addressing Garbage Collection Issues</a></li>
+    <li><a href="{@docRoot}tools/debugging/debugging-memory.html">Investigating Your RAM Usage</a></li>
+  </ol>
+
+</div>
+</div>
+
+
+<p>
+  When you're monitoring memory usage in the Memory Monitor you can, at the same time, dump a
+  snapshot of the Java heap to an Android-specific Heap/CPU Profiling (HPROF) file. The HPROF Viewer
+  displays classes, instances of each class, and a reference tree to help you track memory usage
+  and find memory leaks. HPROF is a binary heap dump format originally supported by J2SE.
+</p>
+<h2 id="why">
+  Why Look at the Java Heap?
+</h2>
+<p>The Java heap display does the following:</p>
+
+<ul>
+  <li>Shows snapshots of a number of objects allocated by type.
+  </li>
+
+  <li>Samples data every time a garbage collection event occurs naturally or is triggered by you.
+  </li>
+
+  <li>Helps identify which object types might be involved in memory leaks.
+  </li>
+</ul>
+
+<p>
+  However, you have to look for changes over time yourself by tracking what's happening in the
+  graph.
+</p>
+
+<p>
+  The HPROF Analyzer finds the following potential issues:
+</p>
+
+<ul>
+  <li>All destroyed activity instances that are reachable from garbage collection roots.
+  </li>
+
+  <li>Where the target program has strings that repeat values.
+  </li>
+</ul>
+
+<p>
+  A dominator is at the top of a tree. If you remove it, you also remove the branches of the tree
+  it dominates, so it’s a potential way to free memory.
+</p>
+
+<h2 id="display">
+  Understanding the HPROF Viewer Display
+</h2>
+
+<p>
+  The HPROF Viewer looks similar to the following figure:
+</p>
+<img src="{@docRoot}images/tools/am-hprofviewer.png" />
+<p>
+  The tool displays the following information:
+</p>
+
+<table>
+  <tr>
+    <th scope="col">Column</th>
+    <th scope="col">Description</th>
+  </tr>
+
+  <tr>
+    <td><strong>Class Name</strong></td>
+    <td>The Java class responsible for the memory.</td>
+  </tr>
+
+  <tr>
+    <td><strong>Total Count</strong></td>
+    <td>Total number of instances outstanding.</td>
+  </tr>
+  <tr>
+    <td><strong>Heap Count</strong></td>
+    <td>Number of instances in the selected heap.</td>
+  </tr>
+  <tr>
+    <td><strong>Sizeof</strong></td>
+    <td>Size of the instances (currently, 0 if the size is variable).</td>
+  </tr>
+  <tr>
+    <td><strong>Shallow Size</strong></td>
+    <td>Total size of all instances in this heap.</td>
+  </tr>
+  <tr>
+    <td><strong>Retained Size</strong></td>
+    <td>Size of memory that all instances of this class is dominating.</td>
+  </tr>
+  <tr>
+    <td><strong>Instance</strong></td>
+    <td>A specific instance of the class.</td>
+  </tr>
+  <tr>
+    <td><strong>Reference Tree</strong></td>
+    <td>References that point to the selected instance, as well as references pointing to the
+      references.</td>
+  </tr>
+  <tr>
+    <td><strong>Depth</strong></td>
+    <td>The shortest number of hops from any GC root to the selected instance.</td>
+  </tr>
+  <tr>
+    <td><strong>Shallow Size</strong></td>
+    <td>Size of this instance.</td>
+  </tr>
+  <tr>
+    <td><strong>Dominating Size</strong></td>
+    <td>Size of memory that this instance is dominating.</td>
+  </tr>
+</table>
+
+<p>If you click <strong>Capture Analysis</strong>, the HPROF Analyzer appears: </p>
+<img src="{@docRoot}images/tools/am-hprofanalyzer.png" />
+<p>You can detect leaked activities and find duplicate strings with the HPROF Analyzer.</p>
+
+<h2 id="hprof-snapshot">
+  Taking and Displaying a Snapshot of the Java Heap
+</h2>
+
+<p>
+  To examine a snapshot of the Java heap:
+</p>
+
+<ol>
+  <li><a href="{@docRoot}tools/help/am-memory.html#displaying">Display a running app in the Memory
+    Monitor</a>.</li>
+  <li>Click Dump Java Heap
+    <img src="{@docRoot}images/tools/am-idump.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Dump Java Heap icon" />.
+  </li>
+
+
+<p>
+  When the icon on the Memory Monitor display changes from
+  <img src="{@docRoot}images/tools/am-idumpstart.png"
+  style="vertical-align:sub;margin:0;height:17px" alt="Dump Java Heap Start icon" /> to
+  <img src="{@docRoot}images/tools/am-idumpend.png" style="vertical-align:sub;margin:0;height:17px"
+  alt="Dump Java Heap End icon" />, the file is ready. Android Studio creates the heap snapshot
+  file with the
+  filename <code><em>package_yyyy.mm.dd_hh.mm.ss</em>.hprof</code> using
+  the activity package (or project) name, year, month, day, hour, minute, and second of the
+  capture, for example,
+  <code>com.android.calc_2015.11.17_14.58.48.hprof</code>.
+</p>
+<p>
+  The HPROF Viewer appears.
+</p>
+</ol>
+
+<h2 id="hprof-viewing">Viewing a Saved HPROF File</h2>
+<p>After you do a heap dump, Android Studio automatically stores it so you can view it again.
+ </p>
+ <p>To view an HPROF file in the HPROF Viewer:</p>
+
+<ol>
+<li>Click
+<img src="{@docRoot}images/tools/am-icaptures.png"
+style="vertical-align:sub;margin:0;height:17px"
+  alt="Captures icon" /> in the main window.</li>
+<p>Or select <strong>View</strong> > <strong>Tools Windows</strong> >
+<strong>Captures</strong>.</p>
+<p>The <em>Captures</em> window appears.</p>
+<li>Open the <strong>Heap Snapshot</strong> folder.</li>
+
+
+  <li>Double-click the file to view it in the HPROF Viewer.
+  </li>
+<p>
+  The HPROF Viewer appears.
+</p>
+
+
+  <li>Select the Heap menu option you want to display:
+    <ul>
+      <li>
+        <strong>App heap</strong> - The heap used by the current app.
+      </li>
+
+      <li><strong>Image heap</strong> - The memory mapped copy of the
+      current app on disk.
+      </li>
+
+
+  <li>
+    <strong>Zygote heap</strong> - The common set of libraries and runtime classes and data that
+    all apps are forked
+    from. The zygote space is created during device startup and is never allocated into.
+  </li>
+
+    </ul>
+
+      <li>Select the View menu option you want to display:
+        <ul>
+          <li>
+            <strong>Class List View</strong>
+          </li>
+
+              <li>
+                <strong>Package Tree View</strong>
+              </li>
+            </ul>
+    </ol>
+
+
+<h2 id="hprof-diving">
+  Diving into Heap Dump Data in the HPROF Viewer
+</h2>
+<p>The following steps outline the typical workflow:</p>
+<ol>
+<li>In the HPROF Viewer, select a class name. </li>
+<li>Select an instance of that class.</li>
+<li>Examine the reference tree.</li>
+<li>Right-click an item to <strong>Jump to source</strong> or <strong>Go to instance</strong>,
+  as needed.</li>
+</ol>
+
+
+
+<h2 id="hprof-analyzing">Analyzing Heap Dump Data in the HPROF Analyzer</h2>
+<p>You can detect leaked activities and find duplicate strings with the HPROF Analyzer.
+ </p>
+ <p>To use the HPROF Analyzer:</p>
+<ol>
+<li>In the <em>Captures</em> window, double-click an <code>.hprof</code> file to display it in the
+  HPROF Viewer. </li>
+<li>Click <strong>Capture Analysis</strong> on the right side of the main Android Studio window.</li>
+
+
+<p>The HPROF Analyzer appears to the right of the HPROF Analyzer, by default.</p>
+
+
+
+<li>In the <strong>Analyzer Tasks</strong> list, select the items you want to find.</li>
+<li>Click Perform Analysis <img src="{@docRoot}images/tools/am-iperformanalysis.png"
+  style="vertical-align:sub;margin:0;height:17px" alt="Perform Analysis icon" />.</li>
+<li>Examine the items in <strong>Analysis Results</strong>. Click an item to display it in the
+  HPROF Viewer.</li>
+</ol>
+
+
+
+<h2 id="hprof-sorting">Sorting Heap Dump Data</h2>
+<p>To sort heap dump data:</p>
+<ul>
+<li>In the HPROF Viewer, click a column heading to sort the table by ascending or descending
+  order. </li>
+</ul>
+
+
+<h2 id="hprof-source">Displaying Java Source</h2>
+<p>For some items displayed in the HPROF Viewer, you can go straight to its
+source code.
+</p>
+<p>To display Java source:</p>
+<ul>
+<li>In the HPROF Viewer, right-click a class, instance, or item in the reference tree, and then
+  select <strong>Jump to Source</strong>. </li>
+
+
+<p>The source code appears in the Code Editor.</p>
+</ul>
+
+<h2 id="hprof-files">Working with HPROF Files</h2>
+<p>You can rename, locate, and delete an HPROF file from within Android Studio.
+You can also convert it to standard HPROF format to use with other analysis
+tools.</p>
+
+<h3 id="hprof-renaming">Renaming an HPROF file</h3>
+
+<p>If you rename a file from within Android Studio, it continues to appear in
+the <em>Captures</em> window.</p>
+<p>To rename an HPROF file:</p>
+<ol>
+<li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>. </li>
+<li>In the dialog, specify the name of the file and click <strong>OK</strong>.</li>
+</ol>
+
+
+<h3 id="hprof-locating">Locating a heap dump file on disk</h3>
+<p>You can quickly discover where Android Studio stored HPROF files on disk.</p>
+
+
+<p>To locate an HPROF file on disk: </p>
+<ul>
+<li>In the <em>Captures</em> window, right-click a heap snapshot file and select
+  <strong>Show</strong> or <strong>Reveal</strong>.</li>
+
+<p>Android Studio opens an operating system file browser displaying the location where the file
+  resides.</p>
+</ul>
+<p class="note"><strong>Note:</strong> If you move an HPROF file, Android Studio no longer
+  displays it in the <em>Captures</em> window. To display it, use
+  <strong>File</strong> &gt; <strong>Open</strong>. Also, if you want to rename the file, do it
+  from the <em>Captures</em> window and not in the operating system file browser. </p>
+
+<h3 id="hprof-deleting">Deleting a heap dump file</h3>
+
+<p>To delete a heap dump file: </p>
+<ul>
+<li>In the <em>Captures</em> window, right-click a heap snapshot file and select
+  <strong>Delete</strong>.</li>
+
+<p>Android Studio deletes the file from the <em>Captures</em> dialog and from disk. </p>
+</ul>
+
+<h3 id="hprof-converting">Converting a heap dump file to standard HPROF format</h3>
+<p>You can convert an HPROF file to standard format so you can use it outside of Android Studio with
+  other analysis tools. </p>
+  <p>To convert an HPROF file:</p>
+<ol>
+<li>In the <em>Captures</em> window, right-click a heap snapshot file and select <strong>Export to
+  standard .hprof</strong>.</li>
+<li>In the <em>Convert Android Java Heap Dump</em> dialog, specify a filename and click
+  <strong>OK</strong>.</li>
+
+
+<p>Android Studio creates a binary HPROF file in the location you specified.</p>
+</ol>
diff --git a/docs/html/tools/help/am-logcat.jd b/docs/html/tools/help/am-logcat.jd
index 57da848..9e26bca 100644
--- a/docs/html/tools/help/am-logcat.jd
+++ b/docs/html/tools/help/am-logcat.jd
@@ -1,7 +1,12 @@
 page.title=logcat Monitor
 parent.title=Android Monitor
 parent.link=android-monitor.html
-page.tags=monitor
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the logcat Monitor to view system and user-defined log messages. You can filter the messages to display just the items that interest you.
+page.image=tools/help/thumbnails/am-logcatmon2.png
+page.article=true
+
 @jd:body
 <div id="qv-wrapper">
   <div id="qv">
@@ -43,16 +48,13 @@
       </li>
 
       <li>
-        <a href="#printing">Printing the Log</a>
+        <a href="#printing">Printing and Writing to a File</a>
       </li>
 
       <li>
-        <a href="#clearing">Clearing the Log</a>
+        <a href="#clearing">Clearing and Restarting the Log</a>
       </li>
 
-      <li>
-        <a href="#restarting">Restarting the Log</a>
-      </li>
     </ol>
 
     <h2>
@@ -63,58 +65,31 @@
       <li>
         <a href="{@docRoot}tools/debugging/debugging-log.html">Reading and Writing Logs</a>
       </li>
-      <li>
-        <a href="{@docRoot}tools/help/android-monitor.html">Android Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
-
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
     </ol>
 
-    <h2>
-      Dependencies and Prerequisites
-    </h2>
-
-    <ul>
-      <li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-      <strong>Enable ADB Integration</strong>.
-      </li>
-  <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-    </ul>
   </div>
 </div>
 
 <p>
   The Android logging system provides a mechanism for collecting and viewing system debug output.
-  logcat Monitor displays messages that you added to your app by using the <a href=
-  "{@docRoot}reference/android/util/Log.html">Log</a> class, as well as system
-  messages, such as stack traces when the emulator throws an error or a garbage collection occurs.
-  The monitor displays messages in real time and also keeps a history so you can view older
+  The logcat Monitor displays system messages, such as when a garbage collection occurs, as well as
+  messages that you added to your app by using the <a href=
+  "{@docRoot}reference/android/util/Log.html">Log</a> class.
+  It displays messages in real time and also keeps a history so you can view older
   messages.
 </p>
 
 <p>
   To display just the information of interest, you can create filters, modify how much information
   is displayed in messages, set priority levels, display messages produced by app code
-  only, and search the log. By default, logcat Monitor shows the log output related to the running
-  application only.
+  only, and search the log. By default, the logcat Monitor shows the log output related to the
+  most recently run app only.
 </p>
 
 <p>
-  You can traverse the stack trace when your app throws an exception, as well as view the
-  associated code. This feature can help you fix exceptions and improve app operation.
+  When an app throws an exception, the logcat Monitor shows a message followed by the associated
+  stack trace containing links to
+  the code. This feature can help you fix errors and improve app operation.
 </p>
 
 <h2 id="format">
@@ -125,9 +100,9 @@
   Every Android log message has a tag and a priority associated with it. The tag of a system
   log message
   is a short string indicating the system component from which the message originates (for example,
-  <code>ActivityManager</code>). A user-defined tag can be any string that you find helpful, such
-  as the name of the current class (the recommended tag). You define it in a <code>Log</code>
-  method call, for example:
+  {@link android.app.ActivityManager}). A user-defined tag can be any string that you find helpful,
+  such as the name of the current class (the recommended tag). You define it in a
+  {@link android.util.Log} method call, for example:
 </p>
 
 <pre>
@@ -189,31 +164,38 @@
 </h2>
 
 <p>
-  Follow these steps:
+  To display the log messages for a particular app:
 </p>
 
 <ol>
-  <li>Optionally connect a hardware device.
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
   </li>
-
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on a hardware device or
+  emulator.
+  </li>
   <li>
-    <a href="{@docRoot}tools/help/android-monitor.html#displaying">Display Android Monitor</a>.
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
   </li>
 
   <li>Click the <strong>logcat</strong> tab.
   </li>
 
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run it</a> on a hardware device or
-  emulator.
-  </li>
+
 <p>
-  By default, the logcat Monitor displays messages for the app running on the device or emulator:
+  By default, the logcat Monitor displays just the log messages for your app running on the
+  device or emulator:
 </p>
-<img src="{@docRoot}images/tools/am-logcatmon.png" />
+<img src="{@docRoot}images/tools/am-logcatmon2.png" />
 <p>
   To change this default, see <a href="#filtering">Filtering logcat Messages</a>.
 </p>
+<li>Optionally <a href=
+  "{@docRoot}tools/help/am-basics.html#switching">select a different device, emulator, or process</a>.
+  </li>
 </ol>
 
 <h2 id="level">
@@ -221,17 +203,17 @@
 </h2>
 
 <p>
-  You can control how many messages appear in logcat Monitor by setting the log level. You can
+  You can control how many messages appear in the logcat Monitor by setting the log level. You can
   display all messages, or just the messages indicating the most severe conditions.
 </p>
 
 <p>
-  Remember that logcat Monitor continues to collect all messages regardless of the log level setting.
-  The setting just determines what logcat Monitor displays.
+  Remember that the logcat Monitor continues to collect all messages regardless of the log level setting.
+  The setting just determines what the logcat Monitor displays.
 </p>
 
 <p>
-  Follow this step:
+  To set the log level:
 </p>
 
 <ul>
@@ -259,7 +241,7 @@
       </li>
 
       <li>
-        <strong>Error</strong> - Show issues that have caused errors, as well as the message levels
+        <strong>Error</strong> - Show issues that have caused errors, as well as the message level
         lower in this list.
       </li>
 
@@ -275,7 +257,7 @@
     </h2>
 
     <p>
-      You can search the messages currently displayed in logcat Monitor. Follow these steps:
+      To search the messages currently displayed in the logcat Monitor:
     </p>
 
     <ol>
@@ -292,7 +274,7 @@
     </p>
   </li>
 
-  <li>Press <strong>Enter</strong> to store the sequence in the menu during this session.
+  <li>Press Enter to store the search string in the menu during this session.
   </li>
 
   <li>To repeat a search, choose it from the search menu. Select or deselect
@@ -310,12 +292,12 @@
 
     <p class="note">
       <strong>Note:</strong> The filter applies to your full logcat history, not just those messages
-      currently displayed in logcat Monitor. Make sure your other display options are set
+      currently displayed in the logcat Monitor. Make sure your other display options are set
       appropriately so you can see the filter output you want to examine.
     </p>
 
     <p>
-      To define and apply a filter, follow these steps:
+      To define and apply a filter:
     </p>
 
     <ol>
@@ -323,15 +305,18 @@
         <ul>
           <li>
             <strong>Show only selected application</strong> - Display the messages produced by the
-            app code only.
+            app code only (the default). The logcat Monitor filters the log messages using the PID
+            of the active app.
           </li>
 
           <li>
-            <strong>No Filters</strong> - Apply no filters (the default).
+            <strong>No Filters</strong> - Apply no filters. The logcat Monitor
+            displays all log messages from the device, regardless of which process you selected.
           </li>
 
           <li>
-            <strong>Edit Filter Configuration</strong> - Create or modify a custom filter.
+            <strong>Edit Filter Configuration</strong> - Create or modify a custom filter. For
+            example, you could create a filter to view log messages from two apps at the same time.
           </li>
         </ul>
 
@@ -386,7 +371,7 @@
             </ul>
 
             <li>
-              Click <strong>+</strong> to add it to the left pane.
+              Click <strong>+</strong> to add the filter definition to the left pane.
             </li>
 
             <p>
@@ -398,6 +383,14 @@
               <strong>Cancel</strong>, any filter additions or modifications are lost.
             </li>
             </ol>
+            <li>
+              Make sure you see the log messages you want to examine.
+            </li>
+             <p>
+              If you don't think you see the log messages you want, try selecting
+              <strong>No filters</strong> and <a href="#searching">searching</a> for particular
+              log messages.
+            </p>
             </ol>
 
             <h2 id="logheader">
@@ -405,7 +398,7 @@
             </h2>
 
             <p>
-              You can customize the header display to show just the information you’re interested
+              To customize the header display to show just the information you’re interested
               in:
             </p>
 
@@ -440,7 +433,9 @@
               in the Code Editor. If needed (and possible), the decompiler derives source code that
               you can view.
             </p>
-
+             <p>
+              To move up and down the stack trace, and view the associated code in the Code Editor:
+            </p>
             <ul>
               <li>Click Up the Stack Trace <img src="{@docRoot}images/tools/am-iupstack.png"
                 style="vertical-align:sub;margin:0;height:17px" alt="Up the Stack Trace icon" />
@@ -460,8 +455,11 @@
             </h2>
 
             <p>
-              Clicking a particular message stops the display of messages. You can quickly move to
-              the end of the log to see the real-time message flow.
+              Clicking a particular message stops the display of messages.
+            </p>
+            <p>
+              To quickly move to
+              the end of the log to see the real-time message flow:
             </p>
 
 <ul>
@@ -477,25 +475,48 @@
 </ul>
 
 <h2 id="printing">
-  Printing the Log
+  Printing and Writing to a File
 </h2>
 <p>
-  Follow these steps:
+  To preserve log information, you can send the log to a printer, write the log to a PDF file, or
+  copy and paste the log into a text file.
+</p>
+<p>
+  To print the log or write it to a PDF file:
 </p>
 <ol>
   <li>Click Print <img src="{@docRoot}images/tools/am-iprint.png"
     style="vertical-align:sub;margin:0;height:17px" alt="Print icon" />.
   </li>
   <li>
-    In the <em>Print</em> dialog, optionally change print parameters, and then click
+    In the Android Studio <em>Print</em> dialog, optionally change print parameters, and then click
     <strong>Print</strong>.
+  </li>
+  <li>
+    In the operating system <em>Print</em> dialog, optionally change print parameters, and then click
+    <strong>Print</strong>.
+  </li>
+  <p>
+  You can set the parameters to send the log to a printer or write it to a PDF file.
+</p>
+</ol>
+<p>
+  To copy the log to a text file:
+</p>
+<ol>
+  <li>In the logcat Monitor, select and then copy log text.
+  </li>
+  <p>Press Ctrl+A (⌘A) to select all.</p>
+  <li>
+    Open a text editor and paste the text into a file.
+  </li>
 </ol>
 
 <h2 id="clearing">
-  Clearing the Log
+  Clearing and Restarting the Log
 </h2>
 <p>
-  To clear (flush) the entire log, follow this step:
+  To clear (flush) the entire log:
 </p>
 <ul>
   <li>Click Clear logcat <img src="{@docRoot}images/tools/am-iclear.png"
@@ -504,14 +525,8 @@
 </ul>
 
 
-
-<h2 id="restarting">
-  Restarting the Log
-</h2>
-
 <p>
-  If there is a problem and the log is no longer progressing, you can restart the log. Follow this
-  step:
+  If there's a problem and the log is no longer progressing, you can restart the log:
 </p>
 
 <ul>
diff --git a/docs/html/tools/help/am-memory.jd b/docs/html/tools/help/am-memory.jd
index 24006cd..20c6934 100644
--- a/docs/html/tools/help/am-memory.jd
+++ b/docs/html/tools/help/am-memory.jd
@@ -1,7 +1,12 @@
 page.title=Memory Monitor
 parent.title=Android Monitor
 parent.link=android-monitor.html
-page.tags=monitor
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Memory Monitor to evaluate memory usage and find deallocated objects, locate memory leaks, and track the amount of memory the connected device is using.
+page.image=tools/help/thumbnails/am-memorymon.png
+page.article=true
+
 @jd:body
 
 <div id="qv-wrapper">
@@ -17,31 +22,7 @@
   </li>
   <li><a href="#displaying">Displaying a Running App in the Memory Monitor</a></li>
   <li><a href="#forcing">Forcing a Garbage Collection Event</a></li>
-  <li><a href="#dumping">Dumping and Analyzing the Java Heap</a>
-    <ol>
-      <li><a href="#hprof-snapshot">Taking and displaying a snapshot of the Java heap</a></li>
-      <li><a href="#hprof-diving">Diving into heap dump data in the HPROF Viewer</a></li>
-      <li><a href="#hprof-analyzing">Analyzing heap dump data in the HPROF Analyzer</a></li>
-      <li><a href="#hprof-sorting">Sorting heap dump data</a></li>
-      <li><a href="#hprof-source">Displaying Java source</a></li>
-      <li><a href="#hprof-viewing">Viewing a saved HPROF file</a></li>
-      <li><a href="#hprof-renaming">Renaming an HPROF file</a></li>
-      <li><a href="#hprof-locating">Locating a heap dump file on disk</a></li>
-      <li><a href="#hprof-deleting">Deleting a heap dump file</a></li>
-      <li><a href="#hprof-converting">Converting a heap dump file to standard HPROF format</a></li>
-    </ol>
-    </li>
-  <li><a href="#tracking">Tracking and Analyzing Memory Allocation</a>
-      <ol>
-      <li><a href="#alloc-snapshot">Taking and displaying a snapshot of allocation data</a></li>
-      <li><a href="#alloc-sorting">Sorting allocation data</a></li>
-      <li><a href="#alloc-source">Displaying Java source</a></li>
-      <li><a href="#alloc-viewing">Viewing a saved allocation tracking file</a></li>
-      <li><a href="#alloc-renaming">Renaming an allocation tracking file</a></li>
-      <li><a href="#alloc-locating">Locating an allocation tracking file</a></li>
-      <li><a href="#alloc-deleting">Deleting an allocation tracking file</a></li>
-    </ol>
-    </li>
+  <li><a href="#snapshot">Taking a Snapshot of the Java Heap and Memory Allocation</a></li>
 </ol>
 
  <h2>See also</h2>
@@ -49,53 +30,8 @@
     <li><a href="{@docRoot}training/articles/memory.html">Managing Your App's Memory</a></li>
     <li><a href="{@docRoot}guide/practices/verifying-apps-art.html#GC_Migration">Addressing Garbage Collection Issues</a></li>
     <li><a href="{@docRoot}tools/debugging/debugging-memory.html">Investigating Your RAM Usage</a></li>
-
-    <li>
-        <a href="{@docRoot}tools/help/android-monitor.html">Android Monitor</a>
-      </li>
-    <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
-
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
   </ol>
 
-
-<h2>
-  Dependencies and Prerequisites
-</h2>
-
-<ul>
-  <li>
-    Make sure your development computer detects your hardware device, which often happens
-  automatically when you connect it to a USB port.
-  </li>
-<li>
-    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
-    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
-    <strong>Developer Options</strong> on the device or emulator.
-  </li>
-
-  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
-  <code>build.gradle</code> file (it’s initially set by default).
-  </li>
-
-  <li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-  <strong>Enable ADB Integration</strong>.
-  </li>
-
-   <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-</ul>
-
 </div>
 </div>
 
@@ -107,7 +43,7 @@
 </p>
 
 <ul>
-  <li>Show a graph of available and allocated memory over time.
+  <li>Show a graph of available and allocated Java memory over time.
   </li>
 <li>Show garbage collection (GC) events
   over time.
@@ -227,10 +163,7 @@
 
 <p>
   One way to optimize memory usage is to analyze large arrays. For example, can you reduce the size
-  of individual elements in the array to save memory? Does a dominator object point to
-  an element in the array, preventing it from being garbage-collected? If the dominator object
-  directly points to an element in the array, the dominator is either the contiguous memory
-  representing the underlying data of the array, some part of the array, or the array itself.
+  of individual elements in the array to save memory?
 </p>
 
 <p>
@@ -347,25 +280,26 @@
 </h2>
 
 <p>
-  Follow these steps:
+  To display an app running on a particular device or emulator in the Memory Monitor:
 </p>
 
 <ol>
-  <li>Optionally connect a hardware device.
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
   </li>
-
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on a hardware device or
+  emulator.
+  </li>
   <li>
-    <a href=
-    "{@docRoot}tools/help/android-monitor.html#displaying">Display Android Monitor</a>.
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+  <li>Click the <strong>Monitors</strong> tab and <a href=
+  "{@docRoot}tools/help/am-basics.html#rearranging">display the Memory Monitor</a>.
   </li>
 
-  <li>Click the <strong>Memory</strong> tab.
-  </li>
-
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run it</a> on a
-  hardware device or emulator.
-  </li>
 
   <li>Enable the Memory Monitor by clicking Pause <img src="{@docRoot}images/tools/am-ipause.png"
     style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect it.
@@ -389,10 +323,10 @@
   <p>In the following figure, the VM initiated the first garbage collection event, while the
     developer forced the second.
 </p>
-<img src="{@docRoot}images/tools/am-gc.png" />
+<img src="{@docRoot}images/tools/am-gc2.png" />
 
   <li>Interact with your app and watch how it affects memory usage in the Memory Monitor. You can
-  identify garbage collection patterns for your app and determine whether they are healthy and what
+  identify garbage collection patterns for your app and determine whether they're healthy and what
   you expect.
   </li>
 
@@ -452,465 +386,20 @@
   </li>
 </ul>
 
-<h2 id="dumping">
-  Dumping and Analyzing the Java Heap
+<h2 id="snapshot">
+  Taking a Snapshot of the Java Heap and Memory Allocation
 </h2>
 
 <p>
-  When you're monitoring memory usage in Android Studio you can, at the same time, dump the Java
-  heap to a heap snapshot in an Android-specific HPROF binary format file. The HPROF Viewer
-  displays classes, instances of each class, and a reference tree to help you track memory usage
-  and find memory leaks. HPROF is a heap dump format originally supported by J2SE.
-</p>
-<p>The Java heap display does the following:</p>
-
-<ul>
-  <li>Shows snapshots of a number of objects allocated by type.
-  </li>
-
-  <li>Samples data every time a garbage collection event occurs naturally or is triggered by you.
-  </li>
-
-  <li>Helps identify which object types might be involved in memory leaks.
-  </li>
-</ul>
-
-<p>
-  However, you have to look for changes over time yourself by tracking what's happening in the
-  graph.
-</p>
-
-<p>
-  The HPROF Analyzer finds the following potential issues:
+  You can take snapshots while the Memory Monitor is running or paused:
 </p>
 
 <ul>
-  <li>All destroyed activity instances that are reachable from garbage collection roots.
+  <li>To take and display a snapshot of the Java heap, see <a href=
+  "{@docRoot}tools/help/am-hprof.html">HPROF Viewer and Analyzer</a>.
   </li>
-
-  <li>Where the target program has strings that repeat values.
+  <li>To take and display a snapshot of memory allocation, see <a href=
+  "{@docRoot}tools/help/am-allocation.html">Allocation Tracker</a>.
   </li>
 </ul>
 
-<p>
-  A dominator is at the top of a tree. If you remove it, you also remove the branches of the tree
-  it dominates, so it’s a potential way to free memory.
-</p>
-
-<h3 id="hprof-snapshot">
-  Taking and displaying a snapshot of the Java heap
-</h3>
-
-<p>
-  To see a snapshot of the Java heap, follow these steps:
-</p>
-
-<ol>
-  <li>While the Memory Monitor is running, click Dump Java Heap
-    <img src="{@docRoot}images/tools/am-idump.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Dump Java Heap icon" />.
-  </li>
-
-
-<p>
-  When the icon on the Memory Monitor display changes from
-  <img src="{@docRoot}images/tools/am-idumpstart.png"
-  style="vertical-align:sub;margin:0;height:17px" alt="Dump Java Heap Start icon" /> to
-  <img src="{@docRoot}images/tools/am-idumpend.png" style="vertical-align:sub;margin:0;height:17px"
-  alt="Dump Java Heap End icon" />, the file is ready. Android Studio creates the heap snapshot
-  file with the
-  filename <code>Snapshot_<em>yyyy.mm.dd_hh.mm.ss</em>.hprof</code> using
-  the year, month, day, hour, minute, and second of the capture, for example,
-  <code>Snapshot_2015.11.17_14.58.48.hprof</code>.
-</p>
-
-  <li>Click <strong>Captures</strong> in the main window.
-  </li>
-
-<p>
-  The <em>Captures</em> window appears.
-</p>
-
-  <li>Double-click the file to view it in the HPROF Viewer.
-  </li>
-
-<p>
-  The HPROF Viewer appears:
-</p>
-<img src="{@docRoot}images/tools/am-hprofviewer.png" />
-<p>
-  The tool displays the following information:
-</p>
-
-<table>
-  <tr>
-    <th scope="col">Column</th>
-    <th scope="col">Description</th>
-  </tr>
-
-  <tr>
-    <td><strong>Class Name</strong></td>
-    <td>The Java class responsible for the memory.</td>
-  </tr>
-
-  <tr>
-    <td><strong>Total Count</strong></td>
-    <td>Total number of instances outstanding.</td>
-  </tr>
-  <tr>
-    <td><strong>Heap Count</strong></td>
-    <td>Number of instances in the selected heap.</td>
-  </tr>
-  <tr>
-    <td><strong>Sizeof</strong></td>
-    <td>Size of the instances (currently, 0 if the size is variable).</td>
-  </tr>
-  <tr>
-    <td><strong>Shallow Size</strong></td>
-    <td>Total size of all instances in this heap.</td>
-  </tr>
-  <tr>
-    <td><strong>Retained Size</strong></td>
-    <td>Size of memory that all instances of this class is dominating.</td>
-  </tr>
-  <tr>
-    <td><strong>Instance</strong></td>
-    <td>A specific instance of the class.</td>
-  </tr>
-  <tr>
-    <td><strong>Reference Tree</strong></td>
-    <td>References that point to the selected instance, as well as references pointing to the
-      references.</td>
-  </tr>
-  <tr>
-    <td><strong>Depth</strong></td>
-    <td>The shortest number of hops from any GC root to the selected instance.</td>
-  </tr>
-  <tr>
-    <td><strong>Shallow Size</strong></td>
-    <td>Size of this instance.</td>
-  </tr>
-  <tr>
-    <td><strong>Dominating Size</strong></td>
-    <td>Size of memory that this instance is dominating.</td>
-  </tr>
-</table>
-
-  <li>Select the Heap menu option you want to display:
-    <ul>
-      <li>
-        <strong>App heap</strong> - The heap used by the current app.
-      </li>
-
-      <li><strong>Image heap</strong> - The memory mapped copy of the
-      current app on disk.
-      </li>
-
-
-  <li>
-    <strong>Zygote heap</strong> - The common set of libraries and runtime classes and data that
-    all apps are forked
-    from. The zygote space is created during device startup and is never allocated into.
-  </li>
-
-    </ul>
-
-      <li>Select the View menu option you want to display:
-        <ul>
-          <li>
-            <strong>Class List View</strong>
-          </li>
-
-              <li>
-                <strong>Package Tree View</strong>
-              </li>
-            </ul>
-    </ol>
-
-
-<h3 id="hprof-diving">
-  Diving into heap dump data in the HPROF Viewer
-</h3>
-<p>The following steps outline the typical workflow:</p>
-<ol>
-<li>In the HPROF viewer, select a class name. </li>
-<li>Select an instance of that class.</li>
-<li>Examine the reference tree.</li>
-<li>Right-click an item to <strong>Jump to source</strong> or <strong>Go to instance</strong>,
-  as needed.</li>
-</ol>
-
-
-
-<h3 id="hprof-analyzing">Analyzing heap dump data in the HPROF Analyzer</h3>
-<p>You can detect leaked activities and find duplicate strings with the HPROF Analyzer.
-  Follow these steps: </p>
-<ol>
-<li>In the <em>Captures</em> window, double-click an <code>.hprof</code> file to display it in the
-  HPROF Viewer. </li>
-<li>Click <strong>Capture Analysis</strong> on the right side of the main Android Studio window.</li>
-
-
-<p>The HPROF Analyzer appears to the right of the HPROF Analyzer, by default: </p>
-
-<img src="{@docRoot}images/tools/am-hprofanalyzer.png" />
-
-<li>In the <strong>Analyzer Tasks</strong> list, select the items you want to find.</li>
-<li>Click Perform Analysis <img src="{@docRoot}images/tools/am-iperformanalysis.png"
-  style="vertical-align:sub;margin:0;height:17px" alt="Perform Analysis icon" />.</li>
-<li>Examine the items in <strong>Analysis Results</strong>. Click an item to display it in the
-  HPROF Viewer.</li>
-</ol>
-
-
-
-<h3 id="hprof-sorting">Sorting heap dump data</h3>
-<p>Follow this step:</p>
-<ul>
-<li>In the HPROF Viewer, click a column heading to sort the table by ascending or descending
-  order. </li>
-</ul>
-
-
-<h3 id="hprof-source">Displaying Java source</h3>
-<p>For some items displayed in the HPROF Viewer, you can go straight to its source code.
-  Follow this step:</p>
-<ul>
-<li>In the HPROF Viewer, right-click a class, instance, or item in the reference tree, and then
-  select <strong>Jump to Source</strong>. </li>
-
-
-<p>The source code appears in the Code Editor.</p>
-</ul>
-
-<h3 id="hprof-viewing">Viewing a saved HPROF file</h3>
-<p>After you do a heap dump, Android Studio automatically stores it so you can view it again.
-  Follow these steps:</p>
-
-<ol>
-<li>Click <strong>Captures</strong> in the main window.</li>
-
-<p>The <em>Captures</em> window appears.</p>
-<li>Open the <strong>Heap Snapshot</strong> folder.</li>
-<li>Double-click the file to view it.</li>
-</ol>
-
-
-<h3 id="hprof-renaming">Renaming an HPROF file</h3>
-
-<p>If you rename a file from within Android Studio, it continues to appear in <em>Captures</em>
-  window. Follow these steps:</p>
-<ol>
-<li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>. </li>
-<li>In the dialog, specify the name of the file and click <strong>OK</strong>.</li>
-</ol>
-
-
-<h3 id="hprof-locating">Locating a heap dump file on disk</h3>
-<p>You can quickly discover where Android Studio stored HPROF files on disk.</p>
-
-
-<p>Follow this step in Android Studio: </p>
-<ul>
-<li>In the <em>Captures</em> window, right-click a heap snapshot file and select
-  <strong>Show in files</strong>.</li>
-
-<p>Android Studio opens an operating system file browser displaying the location where the file
-  resides.</p>
-</ul>
-<p class="note"><strong>Note:</strong> If you move an HPROF file, Android Studio no longer
-  displays it in the <em>Captures</em> window. To display it, use
-  <strong>File</strong> &gt; <strong>Open</strong>. Also, if you want to rename the file, do it
-  from the <em>Captures</em> window and not in the operating system file browser. </p>
-
-<h3 id="hprof-deleting">Deleting a heap dump file</h3>
-
-<p>To delete a heap dump file, follow this step: </p>
-<ul>
-<li>In the <em>Captures</em> window, right-click a heap snapshot file and select
-  <strong>Delete</strong>.</li>
-
-<p>Android Studio deletes the file from the <em>Captures</em> dialog and from disk. </p>
-</ul>
-
-<h3 id="hprof-converting">Converting a heap dump file to standard HPROF format</h3>
-<p>You can convert an HPROF file to standard format so you can use it outside of Android Studio with
-  other analysis tools. Follow these steps: </p>
-<ol>
-<li>In the <em>Captures</em> window, right-click a heap snapshot file and select <strong>Export to
-  standard .hprof</strong>.</li>
-<li>In the <em>Convert Android Java Heap Dump</em> dialog, specify a filename and click
-  <strong>OK</strong>.</li>
-
-
-<p>Android Studio creates a binary HPROF file in the location you specified.</p>
-</ol>
-
-<h2 id="tracking">
-  Tracking and Analyzing Memory Allocation
-</h2>
-
-<p>Android Studio allows you to track memory allocation as it monitors memory use. Tracking memory
-  allocation allows you to monitor where objects are being allocated when you perform certain
-  actions. Knowing these allocations enables you to adjust the method calls related to those actions
-  to optimize app performance and memory use.</p>
-
-<p>The Allocation Tracker does the following:</p>
-<ul>
-<li>Shows when and where your code allocates object types, their size, allocating thread, and stack
-  traces.</li>
-<li>Helps recognize memory churn through recurring allocation/deallocation patterns.</li>
-<li>Help you track down memory leaks when used in combination with the HPROF Viewer. For example,
-  if you see a bitmap object resident on the heap, you can find its allocation location with
-  Allocation Tracker.</li>
-</ul>
-
-
-<p>However, it takes time and experience to learn to interpret the output from this tool.</p>
-
-<h3 id="alloc-snapshot">Taking and displaying a snapshot of allocation data</h3>
-
-<p>Follow these steps:</p>
-<ol>
-<li>While the Memory Monitor is running, click Start Allocation Tracking
-  <img src="{@docRoot}images/tools/am-ialloctracking.png"
-  style="vertical-align:sub;margin:0;height:17px" alt="Start Allocation Tracking icon" />. </li>
-<li>Click Start Allocation Tracking
-  <img src="{@docRoot}images/tools/am-ialloctracking.png"
-  style="vertical-align:sub;margin:0;height:17px" alt="Start Allocation Tracking icon" /> again to
-  deselect it and end the snapshot. </li>
-
-  <p>The Memory Monitor displays the period when it took the snapshot. In the following
-    figure, you can see the snapshot period, as shown on the left. By comparison, when you dump the
-    Java heap, the Memory Monitor displays just the point where the heap snapshot was taken, as
-    shown on the right.</p>
-    <img src="{@docRoot}images/tools/am-dumpalloc.png" />
-
-<p>Android Studio creates the heap snapshot file with the
-  filename <code>Allocations_<em>yyyy.mm.dd_hh.mm.ss</em>.alloc</code> using the year, month, day,
-  hour, minute, and second of the capture, for example,
-  <code>Allocations_2015.11.17_14.58.48.alloc</code>.</p>
-<li>Click <strong>Captures</strong> in the main window.</li>
-
-
-<p>The <em>Captures</em> window appears.</p>
-<li>Double-click the file to view it in the Allocation Tracker. </li>
-<li>Optionally click the graphic icon to display a visual representation of the data.
-  </li>
-<p>
-  The Allocation Tracker appears:
-</p>
-<img src="{@docRoot}images/tools/am-alloctracker.png" />
-<p>
-
-
-<p>The tool displays the following information: </p>
-
-<table>
-  <tr>
-    <th scope="col">Column</th>
-    <th scope="col">Description</th>
-  </tr>
-
-  <tr>
-    <td><strong>Method</strong></td>
-    <td>The Java method responsible for the allocation.</td>
-  </tr>
-  <tr>
-    <td><strong>Count</strong></td>
-    <td>Total number of instances allocated.</td>
-  </tr>
-  <tr>
-    <td><strong>Size</strong></td>
-    <td>The total amount of allocated memory in bytes.</td>
-  </tr>
-
-</table>
-
-
-<li>Select the Group By menu option you want to display: </li>
-<ul>
-<li><strong>Group by Allocator</strong> </li>
-<li><strong>Group by Method</strong></li>
-</ul>
-
-</ol>
-
-
-
-<h3 id="alloc-sorting">Sorting allocation data</h3>
-
-<p>Follow this step:</p>
-<ul>
-<li>In the Allocation Tracker, click a column heading to sort the table by ascending or
-  descending order. </li>
-</ul>
-
-
-<h3 id="alloc-source">Displaying Java source</h3>
-<p>For some items displayed in the Allocation Tracker, you can view the Java source. Follow one of
-  these steps:</p>
-<ul>
-<li>In the Allocation Tracker, right-click a method and then select <strong>Jump to Source</strong>.
-</li>
-<li>In the Allocation Tracker, select a method and then click Jump to Source
-  <img src="{@docRoot}images/tools/am-ijumptosource.png"
-  style="vertical-align:sub;margin:0;height:17px" alt="Jump to Source icon" />. </li>
-</ul>
-
-<p>The source code appears in the Code Editor.</p>
-
-<h3 id="alloc-viewing">Viewing a saved allocation tracking file</h3>
-<p>After you monitor allocation tracking, Android Studio automatically stores it so you can view it
-  again. Follow these steps:</p>
-
-
-<ol>
-<li>Click <strong>Captures</strong> in the main window.</li>
-
-
-<p>The <em>Captures</em> window appears.</p>
-<li>Open the <strong>Allocation Tracking</strong> folder.</li>
-<li>Double-click the file to view it.</li>
-</ol>
-
-
-<h3 id="alloc-renaming">Renaming an allocation tracking file</h3>
-
-<p>If you rename a file from within Android Studio, it continues to appear in the <em>Captures</em>
-  window. Follow these steps:</p>
-<ol>
-<li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>.</li>
-<li>In the <em>Rename</em> dialog, specify the name of the file and click <strong>OK</strong>.</li>
-</ol>
-
-
-<h3 id="alloc-locating">Locating an allocation tracking file</h3>
-<p>You can quickly discover where Android Studio stored allocation tracking files on disk.</p>
-
-
-<p>Follow this step in Android Studio: </p>
-<ul>
-<li>In the <em>Captures</em> window, right-click allocation file and select
-  <strong>Show in Files</strong>.</li>
-
-<p>Android Studio opens an operating system file browser displaying the location where the file
-  resides.</p>
-</ul>
-
-<p class="note"><strong>Note:</strong> If you move an allocation tracking file, Android Studio
-  no longer displays it in the <em>Captures</em> window. To display the file, use
-  <strong>File</strong>
-  &gt; <strong>Open</strong>. Also, rename the file from the <em>Captures</em>
-  window and not in the operating system file browser. </p>
-
-<h3 id="alloc-deleting">Deleting an allocation tracking file</h3>
-
-
-<p>Follow this step: </p>
-<ul>
-<li>In the <em>Captures</em> window, right-click an allocation tracking file and select
-  <strong>Delete</strong>.</li>
-
-<p>Android Studio deletes the file from the <em>Captures</em> dialog and from disk. </p>
-</ul>
diff --git a/docs/html/tools/help/am-methodtrace.jd b/docs/html/tools/help/am-methodtrace.jd
new file mode 100644
index 0000000..7d5f070
--- /dev/null
+++ b/docs/html/tools/help/am-methodtrace.jd
@@ -0,0 +1,266 @@
+page.title=Method Trace
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the CPU Monitor to perform a method trace on your app. View call stack and timing information in the method trace display.
+page.image=tools/help/thumbnails/am_methodtrace.png
+page.article=true
+
+@jd:body
+
+<div id="qv-wrapper">
+<div id="qv">
+  <h2>In this document</h2>
+<ol>
+<li><a href="#display">Understanding the Method Trace Display</a></li>
+  <li><a href="#trace">Performing a Method Trace in the CPU Monitor</a></li>
+  <li><a href="#viewtrace">Viewing a Saved Method Trace</a></li>
+  <li><a href="#sorttrace">Sorting Method Trace Data</a></li>
+  <li><a href="#trace-files">Working with Method Trace Files</a></li>
+</ol>
+
+</div>
+</div>
+
+
+<p>
+  You can start a method trace from the CPU Monitor. It lets you view the call stack and timing
+  information for your app. This information can help you optimize and debug your app.
+</p>
+
+<h2 id="display">
+  Understanding the Method Trace Display
+</h2>
+
+<p>
+  The method trace looks similar to the following figure:
+</p>
+<img src="{@docRoot}images/tools/am-methodtrace.png" alt="Method Trace" />
+<p></p>
+
+<p>The display shows the following information:</p>
+
+<table>
+  <tr>
+    <th scope="col">Field</th>
+    <th scope="col">Description</th>
+  </tr>
+
+  <tr>
+    <td><strong>Name</strong></td>
+    <td>The name of the method.</td>
+  </tr>
+
+  <tr>
+    <td><strong>Invocation Count</strong></td>
+    <td>How many times the method was called.</td>
+  </tr>
+
+  <tr>
+    <td><strong>Inclusive Time (microseconds)</strong></td>
+    <td>Time spent in the method and all of its children, either wall clock or thread time,
+          depending on your selection in the <strong>x-axis</strong> menu.</td>
+  </tr>
+
+  <tr>
+    <td><strong>Exclusive Time (microseconds)</strong></td>
+    <td>Time spent just in the method (excluding time spent in its children), either wall clock
+          or thread time, depending on your selection in the <strong>x-axis</strong> menu.</td>
+  </tr>
+</table>
+
+<p class="note"><strong>Note:</strong> Running the method trace significantly affects CPU timings.
+  Use the method trace to understand the flow of the program, but not for performance timings.</p>
+
+<h2 id="trace">
+  Performing a Method Trace in the CPU Monitor
+</h2>
+
+<p>
+  To perform a method trace:
+</p>
+
+<ol>
+  <li>
+    <a href="{@docRoot}tools/help/am-cpu.html#running">Display a running app in the CPU
+    Monitor</a>.
+  </li>
+
+  <li>Start a trace by clicking Start Method Tracing <img src="{@docRoot}images/tools/am-imethodtrace.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Start Method Tracing icon" /> to
+  select it.
+  </li>
+
+  <li>To stop the trace, click Stop Method Tracing <img src="{@docRoot}images/tools/am-imethodtrace.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Stop Method Tracing icon" /> to
+  deselect it.
+  </li>
+
+<p>
+  The method trace appears in the Code Editor area.
+</p>
+
+<p>
+  Android Studio creates the method trace file
+  with the filename <code><em>package_yyyy.mm.dd_hh.mm.ss</em>.trace</code>
+  using the activity package (or project) name, year, month, day, hour, minute, and second of
+  the capture, for example,
+  <code>com.android.calc_2015.11.17_14.58.48.trace</code>.
+</p>
+  <li>Specify display options:
+    <ul>
+      <li>Select a <strong>Thread</strong>.
+      </li>
+
+      <li>Select an <strong>x-axis</strong> time for the graphic and the method list:
+      </li>
+
+        <ul>
+          <li>
+            <strong>Wall Clock Time</strong> - Total CPU time elapsed between the method call and
+            return.
+          </li>
+
+          <li>
+            <strong>Thread Time</strong> - Total time during which the JRE scheduled the
+            thread during call processing. It’s less than or equal to the Wall Clock Time: less if
+            the JRE interrupted the thread, and equal if it didn’t.
+            The thread might not run continuously; when it’s not executing, that time is excluded.
+            If threads are interrupted often and it’s not by design, the interruptions affect app
+            performance. However, an example of a by-design use is synchronous operations that take
+            a long time, such as file transfers and reads from disk, where the method could be the
+            asynchronous wrapper for the synchronous reader.
+          </li>
+       </ul>
+
+        <li>
+          Optionally select <strong>Color by inclusive time</strong>.
+        </li>
+        </ul>
+
+
+
+        <p>
+          The graphic represents the wall clock or thread time for each method. Hover the cursor
+          over the display to receive information about the method. This information also appears
+          in the table.
+        </p>
+</ol>
+        <h2 id="viewtrace">
+          Viewing a Saved Method Trace
+        </h2>
+
+        <p>
+          After you do a method trace, Android Studio automatically stores it so you can view it
+          again.</p>
+
+          <p>To examine a saved method trace:
+        </p>
+
+        <ol>
+          <li>Click
+          <img src="{@docRoot}images/tools/am-icaptures.png"
+          style="vertical-align:sub;margin:0;height:17px"
+          alt="Captures icon" /> in the main window.
+          </li>
+          <p>Or select <strong>View</strong> > <strong>Tools Windows</strong> >
+          <strong>Captures</strong>.</p>
+
+        <p>
+          The <em>Captures</em> window appears.
+        </p>
+
+      <li>Open the <strong>Methods Tracing</strong> folder.
+      </li>
+
+      <li>Double-click the file to view it.
+      </li>
+</ol>
+
+<h2 id="sorttrace">
+  Sorting Method Trace Data
+</h2>
+
+<p>
+  You can sort the data by method name, count, inclusive time, and exclusive
+  time.</p>
+
+  <p>To sort method trace data:</p>
+
+
+<ul>
+  <li>Click a column heading to sort the table by ascending or descending order.
+  </li>
+</ul>
+
+<h2 id="trace-files">Working with Method Trace Files</h2>
+<p>You can rename, locate, and delete a method trace file from within Android
+Studio.</p>
+
+<h3 id="renametrace">
+  Renaming a method trace file
+</h3>
+
+<p>
+  Rename a method trace file from within Android Studio so it
+  continues to appear in the <em>Captures</em> window.</p>
+
+  <p>To rename a method trace file:
+</p>
+
+<ol>
+  <li>In the <em>Captures</em> window, right-click the file and select <strong>Rename</strong>.
+  </li>
+
+  <li>In the dialog, specify the name of the file and click <strong>OK</strong>.
+  </li>
+</ol>
+
+<h3 id="locatetrace">
+  Locating a method trace file on disk
+</h3>
+
+<p>
+  You can quickly discover where Android Studio stored method trace files on
+  disk.</p>
+
+  <p>To locate a method trace file on disk:
+</p>
+
+
+
+<ul>
+  <li>In the <em>Captures</em> window, right-click a method trace file and
+  select <strong>Show</strong> or <strong>Reveal</strong>.
+  </li>
+
+<p>
+  Android Studio opens an operating system file browser displaying the location where the file
+  resides.
+</p>
+</ul>
+<p class="note">
+  <strong>Note:</strong> If you move a method trace file, Android Studio no longer displays the file
+  in the <em>Captures</em> window. To display it, use <strong>File</strong> &gt;
+  <strong>Open</strong>. Also, rename a file from the <em>Captures</em>
+  window and not in the operating system file browser.
+</p>
+
+<h3 id="deletetrace">
+  Deleting a method trace file
+</h3>
+
+<p>
+  To delete a method trace file:
+</p>
+
+<ul>
+  <li>In the <em>Captures</em> window, right-click a method trace file and select
+  <strong>Delete</strong>.
+  </li>
+</ul>
+
+<p>
+  Android Studio deletes the file from the <em>Captures</em> dialog and from disk.
+</p>
\ No newline at end of file
diff --git a/docs/html/tools/help/am-network.jd b/docs/html/tools/help/am-network.jd
index ae116ac..8129992 100644
--- a/docs/html/tools/help/am-network.jd
+++ b/docs/html/tools/help/am-network.jd
@@ -1,7 +1,12 @@
 page.title=Network Monitor
 parent.title=Android Monitor
 parent.link=android-monitor.html
-page.tags=monitor
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Network Monitor to analyze network requests, including how and when your app transfers data. Preserve battery life by optimizing network use.
+page.image=tools/help/thumbnails/am-networkmon.png
+page.article=true
+
 @jd:body
 
 <div id="qv-wrapper">
@@ -11,63 +16,12 @@
   <li><a href="#running">Displaying a Running App in the Network Monitor</a></li>
 </ol>
 
- <h2>See also</h2>
-  <ol>
-    <li>
-        <a href="{@docRoot}tools/help/android-monitor.html">Android Monitor</a>
-      </li>
-    <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
-  </ol>
-
 <h2>Video</h2>
   <ol>
     <li><a href="https://www.youtube.com/watch?v=fEEulSk1kNY"
       class="external-link">Battery Drain and Networking</a></li>
   </ol>
 
-<h2>
-  Dependencies and Prerequisites
-</h2>
-
-<ul>
-  <li>
-    <a href="{@docRoot}tools/building/building-studio.html#RunningOnDeviceStudio">Connect a
-    hardware device</a> to your development computer.
-  </li>
-
-  <li>Make sure your development computer detects your hardware device, which often happens
-  automatically when you connect it to a USB port.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
-    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
-    <strong>Developer Options</strong> on the device.
-  </li>
-
-  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
-  <code>build.gradle</code> file (it’s initially set by default).
-  </li>
-
-  <li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-  <strong>Enable ADB Integration</strong>.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-</ul>
-
 </div>
 </div>
 
@@ -91,32 +45,35 @@
 </h2>
 
 <p>
-  Follow these steps:
+  To display an app running on a particular device in the Network Monitor:
 </p>
 
 <ol>
-  <li>Connect a hardware device.
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
   </li>
-
+  <p>Connect a hardware device; the Network Monitor doesn't monitor an emulator.
+  </p>
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on the hardware device.
+  </li>
   <li>
-    <a href="{@docRoot}tools/help/android-monitor.html#displaying">Display Android Monitor</a>.
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+  <li>Click the <strong>Monitors</strong> tab and <a href=
+  "{@docRoot}tools/help/am-basics.html#rearranging">display the Network Monitor</a>.
   </li>
 
-  <li>Click the <strong>Network</strong> tab.
+  <li>Enable the Network Monitor by clicking Pause <img src="{@docRoot}images/tools/am-ipause.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to deselect it.
   </li>
 
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run it</a> on the hardware device.
-  </li>
-
-  <li>To start the Network Monitor, click Pause <img src="{@docRoot}images/tools/am-ipause.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Pause icon" /> to
-  deselect it.
-  </li>
 <p>
   Any network traffic begins to appear in the Network Monitor:
 </p>
-  <img src="{@docRoot}images/tools/am-networkmon.png" style="vertical-align:sub;margin:0;width:450px" />
+  <img src="{@docRoot}images/tools/am-networkmon2.png" style="vertical-align:sub;margin:0" />
 <p>
   The Network Monitor adds up the amount of time it takes for the device to transmit and receive
   kilobytes of data.
diff --git a/docs/html/tools/help/am-screenshot.jd b/docs/html/tools/help/am-screenshot.jd
new file mode 100644
index 0000000..322616e
--- /dev/null
+++ b/docs/html/tools/help/am-screenshot.jd
@@ -0,0 +1,89 @@
+page.title=Screen Capture
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Screen Capture tool to take a screenshot of the display on a hardware device or the emulator. Optionally display the screenshot within a graphic of a device.
+page.image=tools/help/thumbnails/am_screenshot.png
+page.article=true
+@jd:body
+
+
+<p>
+  You can take a PNG screenshot of the display on a connected device or the emulator. You can use
+  the images for your marketing materials as well as for debugging, for example.
+</p>
+
+
+<h2 id="screencapture">
+  Taking a Screen Capture of the Device
+</h2>
+
+
+<p>
+  To take a screen capture:
+</p>
+<ol>
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
+  </li>
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on
+  a hardware device or emulator.
+  </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+
+  <li>Interact with the display on the device or emulator to stage the image you want.
+  </li>
+
+  <li>Click Screen Capture <img src="{@docRoot}images/tools/am-iscreencapture.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Screen Capture icon" /> in the
+    Android Monitor toolbar.
+  </li>
+  <p>The screenshot appears in a <em>Screenshot Editor</em> window.</p>
+
+<img src="{@docRoot}images/tools/am-screenshot.png" alt="Screen Capture" />
+
+  <li>Optionally change the image:
+    <ul>
+      <li>
+        <strong>Recapture</strong> - Click to take a new screenshot.
+      </li>
+
+      <li>
+        <strong>Rotate</strong> - Click to rotate the image 90 degrees clockwise.
+      </li>
+
+      <li>
+        <strong>Frame Screenshot</strong> - Select this option and choose a device to add an image
+        of the device to the outside of the screenshot. Select <strong>Drop Shadow</strong>,
+        <strong>Screen Glare</strong>, or both to add these effects to your image.
+      </li>
+
+      <li>
+        <strong>Chessboard</strong> and <strong>Grid</strong> - Select an option to display these
+        behind your image.
+      </li>
+
+      <li>
+        <strong>Zoom In</strong>, <strong>Zoom Out</strong>, or <strong>Actual Size</strong> -
+        Click these options to get different perspectives of your image without changing the image
+        itself.
+      </li>
+    </ul>
+    </li>
+      <li>Click <strong>Save</strong> to save the image.
+      </li>
+      </li>
+      <li>In the <em>Save as PNG</em> dialog, specify the location and filename,
+      and then click <strong>OK</strong>.
+      </li>
+      <p>The screenshot file appears in the Code Editor area.</p>
+</ol>
+
+
+
diff --git a/docs/html/tools/help/am-sysinfo.jd b/docs/html/tools/help/am-sysinfo.jd
new file mode 100644
index 0000000..166cc08
--- /dev/null
+++ b/docs/html/tools/help/am-sysinfo.jd
@@ -0,0 +1,205 @@
+page.title=System Information
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the System Information tool to capture <code>dumpsys</code> information about your app. View activity manager, package, memory usage, and graphics state information.
+page.image=tools/help/thumbnails/am_sysinfo.png
+page.article=true
+@jd:body
+<div id="qv-wrapper">
+<div id="qv">
+  <h2>In this document</h2>
+<ol>
+  <li><a href="#sysinfo">Examining System Information for a Running App</a></li>
+  <li><a href="#viewsysinfo">Viewing Saved System Information</a></li>
+  <li><a href="#sysinfo-files">Working with System Information Files</a></li>
+</ol>
+
+</div>
+</div>
+
+<p>
+  You can capture <code>dumpsys</code> output from within Android Monitor and
+  display the file in the Code Editor. The <em>Captures</em> window lists the
+  system information files so you can retrieve the information later for
+  analysis.
+</p>
+
+
+
+<h2 id="sysinfo">
+  Examining System Information for a Running App
+</h2>
+<p>
+  To capture and view a snapshot of system information:
+</p>
+
+<ol>
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
+  </li>
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on
+  a hardware device or emulator.
+  </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+
+  <li>In the toolbar of the Android Monitor main window, click System Information
+    <img src="{@docRoot}images/tools/am-isysteminfo.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="System Information icon" />
+    and then select a menu item.
+  </li>
+
+<p>
+  The menu items display different types of <code><a href=
+  "https://source.android.com/devices/tech/debug/dumpsys.html">dumpsys</a></code>
+  output:
+</p>
+
+<ul>
+  <li>
+    <strong>Activity Manager State</strong> - <code>dumpsys activity</code>
+  </li>
+
+  <li>
+    <strong>Package Information</strong> - <code>dumpsys package</code>
+  </li>
+
+  <li>
+    <strong>Memory Usage</strong> - <code><a href=
+    "{@docRoot}tools/debugging/debugging-memory.html#ViewingAllocations">dumpsys
+    meminfo</a></code>
+  </li>
+
+  <li>
+    <strong>Memory Use Over Time</strong> - <code><a href=
+    "http://android-developers.blogspot.com/2014/01/process-stats-understanding-how-your.html">dumpsys
+    procstats</a></code>
+  </li>
+
+  <li>
+    <strong>Graphics State</strong> - <code><a href=
+    "{@docRoot}training/testing/performance.html">dumpsys gfxinfo</a></code>
+  </li>
+</ul>
+
+<p>
+  The information appears in an editable text file in the Code Editor.
+</p>
+<img src="{@docRoot}images/tools/am-sysinfo.png" alt="System Information" />
+<p>Android Studio creates the system information file with the
+  filename <code><em>package_yyyy.mm.dd_hh.mm.ss</em>.txt</code> using the
+  activity package (or project) name, year, month, day,
+  hour, minute, and second of the capture, for example,
+  <code>com.android.calc_2015.11.17_14.58.48.txt</code>.</p>
+</ol>
+
+<h2 id="viewsysinfo">
+Viewing Saved System Information
+</h2>
+
+<p>
+After you take a snapshot of system information, Android Studio automatically
+stores it so you can view it again.</p>
+
+<p>To examine a saved system information file:</p>
+
+<ol>
+          <li>Click
+          <img src="{@docRoot}images/tools/am-icaptures.png"
+          style="vertical-align:sub;margin:0;height:17px"
+          alt="Captures icon" /> in the main window.
+          </li>
+          <p>Or select <strong>View</strong> > <strong>Tools Windows</strong> >
+          <strong>Captures</strong>.</p>
+
+        <p>
+          The <em>Captures</em> window appears.
+        </p>
+
+      <li>Open the <strong>System Information</strong> folder.
+      </li>
+
+      <li>Double-click the file to view it.
+      </li>
+</ol>
+
+
+<h2 id="sysinfo-files">Working with System Information Files</h2>
+<p>You can rename, locate, and delete a system information file from within
+Android Studio.</p>
+
+<h3 id="renamesysinfo">
+  Renaming a system information file
+</h3>
+
+<p>
+  Rename a system information file from within Android Studio so it
+  continues to appear in the <em>Captures</em> window.</p>
+
+  <p>To rename a system information file:
+</p>
+
+<ol>
+  <li>In the <em>Captures</em> window, right-click the file and select
+  <strong>Rename</strong>.
+  </li>
+
+  <li>In the dialog, specify the name of the file and click <strong>OK</strong>.
+  </li>
+</ol>
+
+<h3 id="locatesysinfo">
+  Locating a system information file on disk
+</h3>
+
+<p>
+  You can quickly discover where Android Studio stored system information files
+  on disk.</p>
+
+  <p>To locate a system information file on disk:
+</p>
+
+
+
+<ul>
+  <li>In the <em>Captures</em> window, right-click a system information file and
+  select <strong>Show</strong> or <strong>Reveal</strong>.
+  </li>
+
+<p>
+  Android Studio opens an operating system file browser displaying the location
+  where the file resides.
+</p>
+</ul>
+<p class="note">
+  <strong>Note:</strong> If you move a system information file, Android Studio
+  no longer displays the file
+  in the <em>Captures</em> window. To display it, use <strong>File</strong> &gt;
+  <strong>Open</strong>. Also, rename a file from the <em>Captures</em>
+  window and not in the operating system file browser.
+</p>
+
+<h3 id="deletesysinfo">
+  Deleting a system information file
+</h3>
+
+<p>
+  To delete a system information file:
+</p>
+
+<ul>
+  <li>In the <em>Captures</em> window, right-click a system information file
+  and select <strong>Delete</strong>.
+  </li>
+</ul>
+
+<p>
+  Android Studio deletes the file from the <em>Captures</em> dialog and from
+  disk.
+</p>
diff --git a/docs/html/tools/help/am-video.jd b/docs/html/tools/help/am-video.jd
new file mode 100644
index 0000000..5ecdd11
--- /dev/null
+++ b/docs/html/tools/help/am-video.jd
@@ -0,0 +1,78 @@
+page.title=Video Capture
+parent.title=Android Monitor
+parent.link=android-monitor.html
+meta.tags="android, performance, profiling, tools, monitor"
+page.tags="android", "performance", "profiling", "tools", "monitor"
+page.metaDescription=Use the Video tool to make a video of the display on a hardware device.
+page.image=tools/help/thumbnails/am_video.png
+page.article=true
+@jd:body
+
+
+<p>
+  Android Studio lets you record an MP4 video from your hardware device for a maximum of three
+  minutes. You can use the video for your marketing materials as well as for debugging, for
+  example.
+</p>
+<img src="{@docRoot}images/tools/am-video.png" width="230" alt="Device Video" />
+
+
+
+<h2 id="video">
+  Recording a Video from the Screen
+</h2>
+
+<p>
+  To record a video from a hardware device:
+</p>
+<ol>
+  <li>Meet the <a href=
+  "{@docRoot}tools/help/am-basics.html#byb">prerequisites and dependencies</a>.
+  </li>
+ <li>Open an app project.
+  </li>
+  <li><a href=
+  "{@docRoot}tools/building/building-studio.html#RunningApp">Run the app</a> on
+  a hardware device.
+  </li>
+  <li>
+    <a href="{@docRoot}tools/help/am-basics.html#displaying">Display Android Monitor</a>.
+  </li>
+
+  <li>Interact with the display on the hardware device to stage the start of the video.
+  </li>
+
+  <li>Click Screen Record <img src="{@docRoot}images/tools/am-ivideo.png"
+    style="vertical-align:sub;margin:0;height:17px" alt="Screen Record icon" /> in the
+    Android Monitor toolbar.
+  </li>
+  <p>The screenshot appears in a Screenshot Editor window.</p>
+
+  <li>In the <em>Screen Recorder Options</em> dialog, optionally change the recording options:
+  </li>
+<ul>
+  <li>
+    <strong>Bit Rate</strong> - Type a bit rate. The default is 4 Mbps.
+  </li>
+
+  <li>
+    <strong>Resolution</strong> - Type a width and height value in pixels. The value must be a
+    multiple of 16. The default is the resolution of the device.
+  </li>
+</ul>
+  <li>Click <strong>Start Recording</strong> to start the recording.
+  </li>
+
+  <li>Click <strong>Stop Recording</strong> to stop the recording.
+  </li>
+
+  <li>In the <em>Save As</em> dialog, save the MP4 file.
+  </li>
+
+  <li>In the <em>Screen Recorder</em> dialog, click one of the buttons to show the file location,
+  open the recording in a player, or to dismiss the dialog.
+  </li>
+</ol>
+
+
+
diff --git a/docs/html/tools/help/android-monitor.jd b/docs/html/tools/help/android-monitor.jd
index 4c9f80f..2820db8 100644
--- a/docs/html/tools/help/android-monitor.jd
+++ b/docs/html/tools/help/android-monitor.jd
@@ -8,63 +8,16 @@
 <div id="qv">
   <h2>In this document</h2>
 <ol>
-  <li><a href="#displaying">Displaying Android Monitor</a></li>
-  <li><a href="#profiling">Profiling a Running App in Android Monitor</a></li>
-  <li><a href="#switching">Switching between Devices and Apps</a></li>
-  <li><a href="#screencapture">Taking a Screen Capture of the Device</a></li>
-  <li><a href="#video">Recording a Video from the Screen</a></li>
-  <li><a href="#sysinfo">Examining System Information</a></li>
-  <li><a href="#terminating">Terminating the App</a></li>
-  <li><a href="#rearranging">Rearranging Android Monitor Windows</a></li>
-  <li><a href="#removing">Removing an App from a Device</a></li>
+  <li><a href="#logcat">Log Messages</a></li>
+  <li><a href="#monitors">Performance Monitors</a></li>
+  <li><a href="#data">Data Analysis</a></li>
+  <li><a href="#shots">Screen and Video Captures</a></li>
+  <li><a href="#getstarted">Get Started</a></li>
 </ol>
 
- <h2>See also</h2>
-  <ol>
-    <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
-
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
-
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
-  </ol>
 
 
-<h2>
-  Dependencies and Prerequisites
-</h2>
 
-<ul>
-  <li>In your app, set the <code>debuggable</code> property to <code>true</code> in the manifest or
-  <code>build.gradle</code> file (it’s initially set by default).
-  </li>
-
-    <li>Enable ADB integration through <strong>Tools</strong> &gt; <strong>Android</strong> &gt;
-  <strong>Enable ADB Integration</strong>.
-    </li>
-
-  <li>Make sure your development computer detects your hardware device, which often happens
-  automatically when you connect it to a USB port.
-  </li>
- <li>
-    <a href="{@docRoot}tools/device.html#device-developer-options">Enable</a> <strong><a href=
-    "{@docRoot}tools/device.html#device-developer-options">USB debugging</a></strong> in
-    <strong>Developer Options</strong> on the device or emulator.
-  </li>
-
-  <li>
-    <a href="{@docRoot}tools/help/monitor.html">Android Device Monitor</a> can’t be running.
-  </li>
-</ul>
 
 </div>
 </div>
@@ -72,7 +25,7 @@
 <p>
   Android Monitor helps you to profile the performance of your apps so you can optimize, debug, and
   improve them. It lets you monitor the following aspects of your apps from a hardware device or
-  the Android Studio emulator:
+  the <a href="{@docRoot}tools/devices/emulator.html">Android Emulator</a>:
 </p>
 
 <ul>
@@ -88,375 +41,66 @@
   </li>
 </ul>
 
-<p>
-  Android Monitor contains the logcat, Memory, CPU, GPU, and Network Monitors that you can use
-  separately to examine these aspects of your apps.
-</p>
 
+<p>Android Monitor provides various tools that provide real-time information about your app. It
+  lets you capture data as your app runs and stores it in a file that you can analyze in various
+  viewers. You can also capture screen shots and videos of your app as it runs.</p>
 
-<h2 id="displaying">
-  Displaying Android Monitor
-</h2>
+<h2 id="logcat">Log Messages</h2>
 
-<p>
-  Android Monitor is integrated into the Android Studio main window:
-</p>
+<p>View log messages — in real time and historically — which is useful for debugging.</p>
 
-<ul>
-  <li>To display Android Monitor, click <img src="{@docRoot}images/tools/am-icon.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Android Monitor icon" />, which by default
-  is at the bottom of the main window.
-  </li>
+<div class="dynamic-grid">
+  <div class="resource-widget resource-flow-layout landing col-12"
+    data-query="collection:tools/help/log"
+    data-cardSizes="12x6"
+    data-maxResults="6">
+  </div>
+</div>
 
-  <li>To hide Android Monitor, click <img src="{@docRoot}images/tools/am-icon.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Android Monitor icon" /> again.
-  </li>
-</ul>
-<img src="{@docRoot}images/tools/am-androidmon.png" style="vertical-align:sub;margin:0;width:480px" />
 
-<h2 id="profiling">
-  Profiling a Running App in Android Monitor
-</h2>
+<h2 id="monitors">Performance Monitors</h2>
 
-<p>
-  Follow these steps:
-</p>
+<p>Visualize the behavior and performance of your app.</p>
 
-<ol>
-  <li>Optionally connect a hardware device.
-  </li>
+<div class="dynamic-grid">
+  <div class="resource-widget resource-flow-layout landing col-12"
+    data-query="collection:tools/help/monitor"
+    data-cardSizes="9x6"
+    data-maxResults="6">
+  </div>
+</div>
 
-  <li>
-    <a href="#displaying">Display Android Monitor</a>.
-  </li>
+<h2 id="data">Data Analysis</h2>
 
-  <li>Open an app project and <a href=
-  "{@docRoot}tools/building/building-studio.html#RunningApp">run the app</a> on a device or
-  emulator.
-  </li>
+<p>Android Monitor lets you capture various types of data about your app while it's running and
+  stores it in a file, which you can access whenever is convenient.
+  It lists these files in the <em>Captures</em> window.</p>
 
-  <li>Click the tab for the monitor you want to view and start the monitor, if needed:
-    <ul>
-      <li><a href="{@docRoot}tools/help/am-logcat.html">logcat Monitor</a>
-      </li>
+<div class="dynamic-grid">
+  <div class="resource-widget resource-flow-layout landing col-12"
+    data-query="collection:tools/help/data"
+    data-cardSizes="9x6"
+    data-maxResults="6">
+  </div>
+</div>
 
-      <li><a href="{@docRoot}tools/help/am-memory.html">Memory Monitor</a>
-      </li>
+<h2 id="shots">Screen and Video Captures</h2>
 
-      <li><a href="{@docRoot}tools/help/am-cpu.html">CPU Monitor</a>
-      </li>
+<p>Create screen captures and videos of your app to help with marketing and debugging.
+  </p>
 
-      <li><a href="{@docRoot}tools/help/am-gpu.html">GPU Monitor</a>
-      </li>
+<div class="dynamic-grid">
+  <div class="resource-widget resource-flow-layout landing col-12"
+    data-query="collection:tools/help/shot"
+    data-cardSizes="9x3"
+    data-maxResults="2">
+  </div>
+</div>
 
-      <li>
-        <a href="{@docRoot}tools/help/am-network.html">Network Monitor</a>
-      </li>
-    </ul>
-</ol>
-    <h2 id="switching">
-      Switching between Devices and Apps
-    </h2>
-
-    <p>
-      By default, Android Monitor displays data for your most recently run app. You can switch to
-      another device and app as needed. In addition to currently running apps, you can view
-      information about apps that are no longer running so you can continue to view any information
-      about them that you gathered previously.
-    </p>
-
-    <p>
-      At the top of the Android Monitor main window are two menus listing devices and processes. To
-      switch to another device, process, or both, follow these steps:
-    </p>
-
-    <ol>
-      <li>Select the device or emulator.
-      </li>
-
-    <p>
-      The Device menu lists the devices and emulators that are running or have run during your
-      current session. There are various status messages that can appear in the Device menu:
-    </p>
-
-    <ul>
-      <li>
-        <strong>DISCONNECTED</strong> - You closed an emulator or unplugged a device from the
-        computer.
-      </li>
-
-      <li>
-        <strong>UNAUTHORIZED</strong> - A device needs you to accept the incoming computer
-        connection. For example, if the connected device displays an <em>Allow USB Debugging</em>
-        dialog, click <strong>OK</strong> to allow the connection.
-      </li>
-
-      <li>
-        <strong>OFFLINE</strong> - Android Monitor can’t communicate with a device, even though it
-        has detected that device.
-      </li>
-    </ul>
-
-  <li>Select the process.
-  </li>
-</ol>
-
-<p>
-  The Process menu lists the processes that are running or have run during your current session. If
-  a process is no longer running, the menu displays a status of <strong>DEAD</strong>.
-</p>
-
-<h2 id="screencapture">
-  Taking a Screen Capture of the Device
-</h2>
-
-<p>
-  You can take a PNG screenshot of the display on a connected device or the emulator. You can use
-  the images for your marketing materials as well as for debugging, for example.
-</p>
-<p>
-  Follow these steps:
-</p>
-<ol>
-  <li>
-    <a href="{@docRoot}training/basics/firstapp/running-app.html">Run your
-    app</a> from within Android Studio.
-  </li>
-
-  <li>
-    <a href="#switching">Select the device and the process</a> in the Android Monitor
-    menus, if needed.
-  </li>
-
-  <li>Interact with the display on the device or emulator to stage the image you want.
-  </li>
-
-  <li>Click Screen Capture <img src="{@docRoot}images/tools/am-iscreencapture.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Screen Capture icon" /> in the
-    Android Monitor toolbar.
-  </li>
-  <p>The screenshot appears in a <em>Screenshot Editor</em> window.</p>
-
-  <li>Optionally change the image:
-    <ul>
-      <li>
-        <strong>Reload</strong> - Click to take a new screenshot.
-      </li>
-
-      <li>
-        <strong>Rotate</strong> - Click to rotate the image 90 degrees clockwise.
-      </li>
-
-      <li>
-        <strong>Frame Screenshot</strong> - Select this option and choose a device to add an image
-        of the device to the outside of the screenshot. Select <strong>Drop Shadow</strong>,
-        <strong>Screen Glare</strong>, or both to add these effects to your image.
-      </li>
-
-      <li>
-        <strong>Chessboard</strong> and <strong>Grid</strong> - Select an option to display these
-        behind your image.
-      </li>
-
-      <li>
-        <strong>Zoom In</strong>, <strong>Zoom Out</strong>, or <strong>Actual Size</strong> -
-        Click these options to get different perspectives of your image without changing the image
-        itself.
-      </li>
-    </ul>
-    </li>
-      <li>Click <strong>Save</strong> to save the image.
-      </li>
-</ol>
-
-<h2 id="video">
-  Recording a Video from the Screen
-</h2>
-
-<p>
-  Android Studio lets you record an MP4 video from your hardware device for a maximum of three
-  minutes. You can use the video for your marketing materials as well as for debugging, for
-  example.
-</p>
-<p>
-  Follow these steps:
-</p>
-<ol>
-  <li>
-    <a href="{@docRoot}training/basics/firstapp/running-app.html">Run your
-    app</a> from within Android Studio.
-  </li>
-
-  <li>
-    <a href="#switching">Select the device and the process</a> in the Android Monitor
-    menus, if needed.
-  </li>
-
-  <li>Interact with the display on the device or emulator to stage the start of the video.
-  </li>
-
-  <li>Click Screen Record <img src="{@docRoot}images/tools/am-ivideo.png" style="vertical-align:sub;margin:0;height:17px" alt="Screen Record icon" /> in the Android Monitor toolbar.
-  </li>
-  <p>The screenshot appears in a Screenshot Editor window.</p>
-
-  <li>In the <em>Screen Recorder Options</em> dialog, optionally change the recording options:
-  </li>
-<ul>
-  <li>
-    <strong>Bit Rate</strong> - Type a bit rate. The default is 4 Mbps.
-  </li>
-
-  <li>
-    <strong>Resolution</strong> - Type a width and height value in pixels. The value must be a
-    multiple of 16. The default is the resolution of the device.
-  </li>
-</ul>
-  <li>Click <strong>Start Recording</strong> to start the recording.
-  </li>
-
-  <li>Click <strong>Stop Recording</strong> to stop the recording.
-  </li>
-
-  <li>In the <em>Save As</em> dialog, save the MP4 file.
-  </li>
-
-  <li>In the <em>Screen Recorder</em> dialog, click one of the buttons to show the file location,
-  open the recording in a player, or to dismiss the dialog.
-  </li>
-</ol>
-
-<h2 id="sysinfo">
-  Examining System Information
-</h2>
-<p>
-  You can view <code>dumpsys</code> output from within Android Monitor. Follow these steps:
-</p>
-
-<ol>
-  <li>
-    <a href="{@docRoot}training/basics/firstapp/running-app.html">Run your
-    app</a> from within Android Studio.
-  </li>
-
-  <li>
-    <a href="#switching">Select the device and the process</a> in the Android Monitor
-    menus, if needed.
-  </li>
-
-  <li>Click System Information <img src="{@docRoot}images/tools/am-isysteminfo.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="System Information icon" /> and then a
-    menu item in the Android Monitor
-  toolbar.
-  </li>
-
-<p>
-  The menu items display different types of <code><a href=
-  "https://source.android.com/devices/tech/debug/dumpsys.html">dumpsys</a></code> output:
-</p>
-
-<ul>
-  <li>
-    <strong>Activity Manager State</strong> - <code>dumpsys activity</code>
-  </li>
-
-  <li>
-    <strong>Package Information</strong> - <code>dumpsys package</code>
-  </li>
-
-  <li>
-    <strong>Memory Usage</strong> - <code><a href=
-    "{@docRoot}tools/debugging/debugging-memory.html#ViewingAllocations">dumpsys
-    meminfo</a></code>
-  </li>
-
-  <li>
-    <strong>Memory Use Over Time</strong> - <code><a href=
-    "http://android-developers.blogspot.com/2014/01/process-stats-understanding-how-your.html">dumpsys
-    procstats</a></code>
-  </li>
-
-  <li>
-    <strong>Graphics State</strong> - <code><a href=
-    "{@docRoot}training/testing/performance.html">dumpsys gfxinfo</a></code>
-  </li>
-</ul>
-
-<p>
-  The information appears in an editable text file in the Code Editor.
-</p>
-</ol>
-
-<h2 id="terminating">
-  Terminating the App
-</h2>
-
-<p>
-  If you want to stop an app you’ve run from Android Studio, follow these steps:
-</p>
-
-<ol>
-  <li>
-    <a href="#switching">Select the device and the process</a> in the Android Monitor
-    menus, if needed.
-  </li>
-
-  <li>Click Terminate Application <img src="{@docRoot}images/tools/am-iterminate.png"
-    style="vertical-align:sub;margin:0;height:17px" alt="Terminate App icon" />.
-  </li>
-
-
-<p>
-  The process status changes to <strong>DEAD</strong> in the Processes menu. The emulator or device
-  continues to run, but the app closes. Any running monitors in Android Monitor stop.
-</p>
-</ol>
-
-<h2 id="rearranging">
-  Rearranging Android Monitor Windows
-</h2>
-
-<p>
-  You can rearrange the Android Monitor windows for optimal viewing during your tests:
-</p>
-
-<ul>
-  <li>To reorder the monitors, move the tabs back and forth.
-  </li>
-
-  <li>To move a monitor to a standalone window, grab a tab and move it to a different location on
-  the screen. Or, select <img src="{@docRoot}images/tools/am-igear.png" style="vertical-align:sub;margin:0;height:17px" alt="Gear menu icon" /> &gt; <strong>Floating Mode</strong>.
-  </li>
-
-
-  <li>To dock a standalone window, grab it and move it to the Android Monitor area. Or, select
-  <img src="{@docRoot}images/tools/am-igear.png" style="vertical-align:sub;margin:0;height:17px"
-  alt="Gear menu icon"> &gt; <strong>Floating Mode</strong> to deselect it.
-  </li>
-
-
-  <li>To combine two monitor displays together, grab a tab and move it onto another monitor.
-  </li>
-
-  <li>To hide a monitor, click the <img src="{@docRoot}images/tools/am-ihide.png" style="vertical-align:sub;margin:0;height:17px" alt="Hide icon" /> icon. To make it reappear, click the icon of
-  the monitor on the far right of the row of tabs.
-  </li>
-</ul>
-
-<h2 id="removing">
-  Removing an App from a Device
-</h2>
-
-<p>
-  To remove an app from a device you use for development, use the normal uninstall procedure on the
-  device.
-</p>
-
-<p>
-  If you run a new version of an app from Android Studio that’s been already installed on a
-  hardware device, the device displays an <em>Application Installation Failed</em> dialog. Click
-  <strong>OK</strong> to install the new version of the app.
-</p>
-
-
+<h2 id="getstarted">Get Started</h2>
+<p>To begin using Android Monitor, start with <a href=
+  "{@docRoot}tools/help/am-basics.html">Android Monitor Basics</a>.
+  </p>
 
 
diff --git a/docs/html/tools/help/thumbnails/am-androidmon2.png b/docs/html/tools/help/thumbnails/am-androidmon2.png
new file mode 100644
index 0000000..a4a7571
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-androidmon2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-cpumon.png b/docs/html/tools/help/thumbnails/am-cpumon.png
new file mode 100644
index 0000000..59908c8
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-cpumon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-cpumon2.png b/docs/html/tools/help/thumbnails/am-cpumon2.png
new file mode 100644
index 0000000..6ac6e02
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-cpumon2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-gc2.png b/docs/html/tools/help/thumbnails/am-gc2.png
new file mode 100644
index 0000000..a5e8b6e
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-gc2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-gpumon.png b/docs/html/tools/help/thumbnails/am-gpumon.png
new file mode 100644
index 0000000..a414fe5
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-gpumon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-gpumon2.png b/docs/html/tools/help/thumbnails/am-gpumon2.png
new file mode 100644
index 0000000..5cf51d9
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-gpumon2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-logcatmon2.png b/docs/html/tools/help/thumbnails/am-logcatmon2.png
new file mode 100644
index 0000000..5635935
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-logcatmon2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-memorymon.png b/docs/html/tools/help/thumbnails/am-memorymon.png
new file mode 100644
index 0000000..0fefb27
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-memorymon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am-networkmon.png b/docs/html/tools/help/thumbnails/am-networkmon.png
new file mode 100644
index 0000000..db9c647
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am-networkmon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_alloctracker.png b/docs/html/tools/help/thumbnails/am_alloctracker.png
new file mode 100644
index 0000000..b94713d
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_alloctracker.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_androidmon.png b/docs/html/tools/help/thumbnails/am_androidmon.png
new file mode 100644
index 0000000..6b05230
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_androidmon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_cpumon.png b/docs/html/tools/help/thumbnails/am_cpumon.png
new file mode 100644
index 0000000..c8c0415
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_cpumon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_gpumon.png b/docs/html/tools/help/thumbnails/am_gpumon.png
new file mode 100644
index 0000000..e453e7d
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_gpumon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_hprofviewer.png b/docs/html/tools/help/thumbnails/am_hprofviewer.png
new file mode 100644
index 0000000..342590f
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_hprofviewer.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_iscreencapture.png b/docs/html/tools/help/thumbnails/am_iscreencapture.png
new file mode 100644
index 0000000..68135a7
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_iscreencapture.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_isysteminfo.png b/docs/html/tools/help/thumbnails/am_isysteminfo.png
new file mode 100644
index 0000000..37d77db
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_isysteminfo.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_ivideo.png b/docs/html/tools/help/thumbnails/am_ivideo.png
new file mode 100644
index 0000000..901eaf1
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_ivideo.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_logcatmon.png b/docs/html/tools/help/thumbnails/am_logcatmon.png
new file mode 100644
index 0000000..ca7063c
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_logcatmon.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_methodtrace.png b/docs/html/tools/help/thumbnails/am_methodtrace.png
new file mode 100644
index 0000000..8d5ca4e
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_methodtrace.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_networkmon2.png b/docs/html/tools/help/thumbnails/am_networkmon2.png
new file mode 100644
index 0000000..f55f853
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_networkmon2.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_screenshot.png b/docs/html/tools/help/thumbnails/am_screenshot.png
new file mode 100644
index 0000000..66afff9
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_screenshot.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_sysinfo.png b/docs/html/tools/help/thumbnails/am_sysinfo.png
new file mode 100644
index 0000000..9b5cd17
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_sysinfo.png
Binary files differ
diff --git a/docs/html/tools/help/thumbnails/am_video.png b/docs/html/tools/help/thumbnails/am_video.png
new file mode 100644
index 0000000..209cb0c
--- /dev/null
+++ b/docs/html/tools/help/thumbnails/am_video.png
Binary files differ
diff --git a/docs/html/tools/tools_toc.cs b/docs/html/tools/tools_toc.cs
index c390523..73d4ff3 100644
--- a/docs/html/tools/tools_toc.cs
+++ b/docs/html/tools/tools_toc.cs
@@ -147,6 +147,9 @@
         <div class="nav-section-header">
           <a href="<?cs var:toroot ?>tools/help/android-monitor.html">Android Monitor</a></div>
         <ul>
+          <li><a href="<?cs var:toroot ?>tools/help/am-basics.html"><span
+            class="en">Android Monitor Basics</span></a>
+          </li>
           <li><a href="<?cs var:toroot ?>tools/help/am-logcat.html"><span
             class="en">logcat Monitor</span></a>
           </li>
@@ -162,6 +165,25 @@
           <li><a href="<?cs var:toroot ?>tools/help/am-network.html"><span
             class="en">Network Monitor</span></a>
           </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-hprof.html"><span
+            class="en">HPROF Viewer and Analyzer</span></a>
+           </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-allocation.html"><span
+            class="en">Allocation Tracker</span></a>
+             </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-methodtrace.html"><span
+            class="en">Method Trace</span></a>
+            </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-sysinfo.html"><span
+            class="en">System Information</span></a>
+            </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-screenshot.html"><span
+            class="en">Screen Capture</span></a>
+            </li>
+            <li><a href="<?cs var:toroot ?>tools/help/am-video.html"><span
+            class="en">Video Capture</span></a>
+            </li>
+          </li>
         </ul>
       </li>
 
@@ -217,6 +239,7 @@
       </li>
 
       <li><a href="<?cs var:toroot ?>tools/help/hprof-conv.html">hprof-conv</a></li>
+      <li><a href="<?cs var:toroot ?>tools/help/image-asset-studio.html">Image Asset Studio</a></li>
       <li><a href="<?cs var:toroot ?>tools/help/jobb.html">jobb</a></li>
       <li><a href="<?cs var:toroot ?>tools/help/lint.html">lint</span></a></li>
       <li class="nav-section">
diff --git a/docs/html/training/_book.yaml b/docs/html/training/_book.yaml
index cd4df43..8f8fab2 100644
--- a/docs/html/training/_book.yaml
+++ b/docs/html/training/_book.yaml
@@ -4,8 +4,9 @@
   section:
   - title: Building Your First App
     path: /training/basics/firstapp/index.html
-    custom_link_attributes:
-    - description="After you've installed the Android SDK, start with this class to learn the basics about Android app development."
+    path_attributes:
+    - name: description
+      value: After you've installed the Android SDK, start with this class to learn the basics about Android app development.
     section:
     - title: Creating an Android Project
       path: /training/basics/firstapp/creating-project.html
@@ -17,8 +18,9 @@
       path: /training/basics/firstapp/starting-activity.html
   - title: Supporting Different Devices
     path: /training/basics/supporting-devices/index.html
-    custom_link_attributes:
-    - description="How to build your app with alternative resources that provide an optimized user experience on multiple device form factors using a single APK."
+    path_attributes:
+    - name: description
+      value: How to build your app with alternative resources that provide an optimized user experience on multiple device form factors using a single APK.
     section:
     - title: Supporting Different Languages
       path: /training/basics/supporting-devices/languages.html
@@ -28,137 +30,215 @@
       path: /training/basics/supporting-devices/platforms.html
   - title: Managing the Activity Lifecycle
     path: /training/basics/activity-lifecycle/index.html
-    custom_link_attributes:
-    - ja-lang="アクティビティのライフサイクル 管理"
-    - ko-lang="액티비티 수명 주기 관리하기"
-    - pt-br-lang="Como gerenciar o ciclo de vida da atividade"
-    - ru-lang="Управление жизненным циклом операций"
-    - zh-cn-lang="管理活动生命周期"
-    - zh-tw-lang="管理應用行為顯示生命週期"
-    - description="How Android activities live and die and how to create a seamless user experience by implementing lifecycle callback methods."
+    path_attributes:
+    - name: ja-lang
+      value: アクティビティのライフサイクル 管理
+    - name: ko-lang
+      value: 액티비티 수명 주기 관리하기
+    - name: pt-br-lang
+      value: Como gerenciar o ciclo de vida da atividade
+    - name: ru-lang
+      value: Управление жизненным циклом операций
+    - name: zh-cn-lang
+      value: 管理活动生命周期
+    - name: zh-tw-lang
+      value: 管理應用行為顯示生命週期
+    - name: description
+      value: How Android activities live and die and how to create a seamless user experience by implementing lifecycle callback methods.
     section:
     - title: Starting an Activity
       path: /training/basics/activity-lifecycle/starting.html
-      custom_link_attributes:
-      - ja-lang="アクティビティを開始する"
-      - ko-lang="액티비티 시작하기"
-      - pt-br-lang="Iniciando uma atividade"
-      - ru-lang="Запуск операции"
-      - zh-cn-lang="开始活动"
-      - zh-tw-lang="啟動應用行為顯示"
+      path_attributes:
+      - name: ja-lang
+        value: アクティビティを開始する
+      - name: ko-lang
+        value: 액티비티 시작하기
+      - name: pt-br-lang
+        value: Iniciando uma atividade
+      - name: ru-lang
+        value: Запуск операции
+      - name: zh-cn-lang
+        value: 开始活动
+      - name: zh-tw-lang
+        value: 啟動應用行為顯示
     - title: Pausing and Resuming an Activity
       path: /training/basics/activity-lifecycle/pausing.html
     - title: Stopping and Restarting an Activity
       path: /training/basics/activity-lifecycle/stopping.html
-      custom_link_attributes:
-      - ja-lang="アクティビティの一時停止と再開"
-      - ko-lang="액티비티 일시정지 및 재개하기"
-      - pt-br-lang="Pausando e reiniciando uma atividade"
-      - ru-lang="Приостановка и возобновление операции"
-      - zh-cn-lang="暂停和继续活动"
-      - zh-tw-lang="暫停並繼續應用行為顯示"
+      path_attributes:
+      - name: ja-lang
+        value: アクティビティの一時停止と再開
+      - name: ko-lang
+        value: 액티비티 일시정지 및 재개하기
+      - name: pt-br-lang
+        value: Pausando e reiniciando uma atividade
+      - name: ru-lang
+        value: Приостановка и возобновление операции
+      - name: zh-cn-lang
+        value: 暂停和继续活动
+      - name: zh-tw-lang
+        value: 暫停並繼續應用行為顯示
     - title: Recreating an Activity
       path: /training/basics/activity-lifecycle/recreating.html
-      custom_link_attributes:
-      - ja-lang="アクティビティを再作成する"
-      - ko-lang="액티비티 재생성하기"
-      - pt-br-lang="Recriando uma atividade"
-      - ru-lang="Воссоздание операции"
-      - zh-cn-lang="重新创建活动"
-      - zh-tw-lang="重新建立應用行為顯示"
+      path_attributes:
+      - name: ja-lang
+        value: アクティビティを再作成する
+      - name: ko-lang
+        value: 액티비티 재생성하기
+      - name: pt-br-lang
+        value: Recriando uma atividade
+      - name: ru-lang
+        value: Воссоздание операции
+      - name: zh-cn-lang
+        value: 重新创建活动
+      - name: zh-tw-lang
+        value: 重新建立應用行為顯示
   - title: Building a Dynamic UI with Fragments
     path: /training/basics/fragments/index.html
-    custom_link_attributes:
-    - description="How to build a user interface for your app that is flexible enough to present multiple UI components on large screens and a more constrained set of UI components on smaller screens—essential for building a single APK for both phones and tablets."
+    path_attributes:
+    - name: description
+      value: How to build a user interface for your app that is flexible enough to present multiple UI components on large screens and a more constrained set of UI components on smaller screens—essential for building a single APK for both phones and tablets.
     section:
     - title: Creating a Fragment
       path: /training/basics/fragments/creating.html
     - title: Building a Flexible UI
       path: /training/basics/fragments/fragment-ui.html
-      custom_link_attributes:
-      - zh-cn-lang="构建灵活的界面"
+      path_attributes:
+      - name: zh-cn-lang
+        value: 构建灵活的界面
     - title: Communicating with Other Fragments
       path: /training/basics/fragments/communicating.html
   - title: Saving Data
     path: /training/basics/data-storage/index.html
-    custom_link_attributes:
-    - ja-lang="データの保存"
-    - ko-lang="데이터 저장하기"
-    - pt-br-lang="Salvando dados"
-    - ru-lang="Сохранение данных"
-    - zh-cn-lang="保存数据"
-    - zh-tw-lang="儲存資料"
-    - description="How to save data on the device, whether it's temporary files, downloaded app assets, user media, structured data, or something else."
+    path_attributes:
+    - name: ja-lang
+      value: データの保存
+    - name: ko-lang
+      value: 데이터 저장하기
+    - name: pt-br-lang
+      value: Salvando dados
+    - name: ru-lang
+      value: Сохранение данных
+    - name: zh-cn-lang
+      value: 保存数据
+    - name: zh-tw-lang
+      value: 儲存資料
+    - name: description
+      value: How to save data on the device, whether it's temporary files, downloaded app assets, user media, structured data, or something else.
     section:
     - title: Saving Key-Value Sets
       path: /training/basics/data-storage/shared-preferences.html
-      custom_link_attributes:
-      - ja-lang="キー値セットを保存する"
-      - ko-lang="키-값 세트 저장하기"
-      - pt-br-lang="Salvando conjuntos de valor-chave"
-      - ru-lang="Сохранение наборов \"ключ-значение\""
-      - zh-cn-lang="保存键值集"
-      - zh-tw-lang="儲存索引鍵值組"
+      path_attributes:
+      - name: ja-lang
+        value: キー値セットを保存する
+      - name: ko-lang
+        value: 키-값 세트 저장하기
+      - name: pt-br-lang
+        value: Salvando conjuntos de valor-chave
+      - name: ru-lang
+        value: Сохранение наборов "ключ-значение"
+      - name: zh-cn-lang
+        value: 保存键值集
+      - name: zh-tw-lang
+        value: 儲存索引鍵值組
     - title: Saving Files
       path: /training/basics/data-storage/files.html
-      custom_link_attributes:
-      - ja-lang="ファイルを保存する"
-      - ko-lang="파일 저장하기"
-      - pt-br-lang="Salvando arquivos"
-      - ru-lang="Сохранение файлов"
-      - zh-cn-lang="保存文件"
-      - zh-tw-lang="儲存檔案"
+      path_attributes:
+      - name: ja-lang
+        value: ファイルを保存する
+      - name: ko-lang
+        value: 파일 저장하기
+      - name: pt-br-lang
+        value: Salvando arquivos
+      - name: ru-lang
+        value: Сохранение файлов
+      - name: zh-cn-lang
+        value: 保存文件
+      - name: zh-tw-lang
+        value: 儲存檔案
     - title: Saving Data in SQL Databases
       path: /training/basics/data-storage/databases.html
-      custom_link_attributes:
-      - ja-lang="SQL データベースにデータを保存する"
-      - ko-lang="SQL 데이터베이스에 데이터 저장하기"
-      - pt-br-lang="Salvando dados em bancos de dados do SQL"
-      - ru-lang="Сохранение данных в базах данных SQL"
-      - zh-cn-lang="在 SQL 数据库中保存数据"
-      - zh-tw-lang="在 SQL 資料庫中儲存資料"
+      path_attributes:
+      - name: ja-lang
+        value: SQL データベースにデータを保存する
+      - name: ko-lang
+        value: SQL 데이터베이스에 데이터 저장하기
+      - name: pt-br-lang
+        value: Salvando dados em bancos de dados do SQL
+      - name: ru-lang
+        value: Сохранение данных в базах данных SQL
+      - name: zh-cn-lang
+        value: 在 SQL 数据库中保存数据
+      - name: zh-tw-lang
+        value: 在 SQL 資料庫中儲存資料
   - title: Interacting with Other Apps
     path: /training/basics/intents/index.html
-    custom_link_attributes:
-    - ja-lang="他のアプリとの相互操作"
-    - ko-lang="액티비티 수명 주기 관리하기"
-    - pt-br-lang="Interagindo com outros aplicativos"
-    - ru-lang="Взаимодействие с другими приложениями"
-    - zh-cn-lang="与其他应用交互"
-    - zh-tw-lang="與其他應用程式互動"
-    - description="How to build a user experience that leverages other apps available on the device to perform advanced user tasks, such as capture a photo or view an address on a map."
+    path_attributes:
+    - name: ja-lang
+      value: 他のアプリとの相互操作
+    - name: ko-lang
+      value: 액티비티 수명 주기 관리하기
+    - name: pt-br-lang
+      value: Interagindo com outros aplicativos
+    - name: ru-lang
+      value: Взаимодействие с другими приложениями
+    - name: zh-cn-lang
+      value: 与其他应用交互
+    - name: zh-tw-lang
+      value: 與其他應用程式互動
+    - name: description
+      value: How to build a user experience that leverages other apps available on the device to perform advanced user tasks, such as capture a photo or view an address on a map.
     section:
     - title: Sending the User to Another App
       path: /training/basics/intents/sending.html
-      custom_link_attributes:
-      - ja-lang="別のアプリにユーザーを送る"
-      - ko-lang="다른 앱으로 사용자 보내기"
-      - pt-br-lang="Enviando o usuário para outro aplicativo"
-      - ru-lang="Направление пользователя в другое приложение"
-      - zh-cn-lang="向另一个应用发送用户"
-      - zh-tw-lang="將使用者傳送至其他應用程式"
+      path_attributes:
+      - name: ja-lang
+        value: 別のアプリにユーザーを送る
+      - name: ko-lang
+        value: 다른 앱으로 사용자 보내기
+      - name: pt-br-lang
+        value: Enviando o usuário para outro aplicativo
+      - name: ru-lang
+        value: Направление пользователя в другое приложение
+      - name: zh-cn-lang
+        value: 向另一个应用发送用户
+      - name: zh-tw-lang
+        value: 將使用者傳送至其他應用程式
     - title: Getting a Result from the Activity
       path: /training/basics/intents/result.html
-      custom_link_attributes:
-      - ja-lang="アクティビティから結果を取得する"
-      - ko-lang="액티비티로부터 결과 가져오기"
-      - pt-br-lang="Obtendo resultados de uma atividade"
-      - ru-lang="Получение результата операции"
-      - zh-cn-lang="获取活动的结果"
-      - zh-tw-lang="從應用行為顯示取得結果"
+      path_attributes:
+      - name: ja-lang
+        value: アクティビティから結果を取得する
+      - name: ko-lang
+        value: 액티비티로부터 결과 가져오기
+      - name: pt-br-lang
+        value: Obtendo resultados de uma atividade
+      - name: ru-lang
+        value: Получение результата операции
+      - name: zh-cn-lang
+        value: 获取活动的结果
+      - name: zh-tw-lang
+        value: 從應用行為顯示取得結果
     - title: Allowing Other Apps to Start Your Activity
       path: /training/basics/intents/filters.html
-      custom_link_attributes:
-      - ja-lang="他のアプリからのアクティビティの開始を許可する"
-      - ko-lang="다른 앱이 자신의 액티비티를 시작하도록 허용하기"
-      - pt-br-lang="Permitindo que outros aplicativos iniciem sua atividade"
-      - ru-lang="Разрешение другим приложениям на запуск вашей операции"
-      - zh-cn-lang="允许其他应用开始您的活动"
-      - zh-tw-lang="允許其他應用程式啟動您的應用行為顯示"
+      path_attributes:
+      - name: ja-lang
+        value: 他のアプリからのアクティビティの開始を許可する
+      - name: ko-lang
+        value: 다른 앱이 자신의 액티비티를 시작하도록 허용하기
+      - name: pt-br-lang
+        value: Permitindo que outros aplicativos iniciem sua atividade
+      - name: ru-lang
+        value: Разрешение другим приложениям на запуск вашей операции
+      - name: zh-cn-lang
+        value: 允许其他应用开始您的活动
+      - name: zh-tw-lang
+        value: 允許其他應用程式啟動您的應用行為顯示
   - title: Working with System Permissions
     path: /training/permissions/index.html
-    custom_link_attributes:
-    - description="How to declare that your app needs access to features and resources outside of its 'sandbox', and how to request those privileges at runtime."
+    path_attributes:
+    - name: description
+      value: How to declare that your app needs access to features and resources outside of its 'sandbox', and how to request those privileges at runtime.
     section:
     - title: Declaring Permissions
       path: /training/permissions/declaring.html
@@ -172,8 +252,9 @@
   section:
   - title: Sharing Simple Data
     path: /training/sharing/index.html
-    custom_link_attributes:
-    - description="How to take your app interaction to the next level by sharing information with other apps, receive information back, and provide a simple and scalable way to perform Share actions with user content."
+    path_attributes:
+    - name: description
+      value: How to take your app interaction to the next level by sharing information with other apps, receive information back, and provide a simple and scalable way to perform Share actions with user content.
     section:
     - title: Sending Simple Data to Other Apps
       path: /training/sharing/send.html
@@ -183,8 +264,9 @@
       path: /training/sharing/shareaction.html
   - title: Sharing Files
     path: /training/secure-file-sharing/index.html
-    custom_link_attributes:
-    - description="How to provide secure access to a file associated with your app using a content URI and temporary access permissions."
+    path_attributes:
+    - name: description
+      value: How to provide secure access to a file associated with your app using a content URI and temporary access permissions.
     section:
     - title: Setting Up File Sharing
       path: /training/secure-file-sharing/setup-sharing.html
@@ -196,8 +278,9 @@
       path: /training/secure-file-sharing/retrieve-info.html
   - title: Sharing Files with NFC
     path: /training/beam-files/index.html
-    custom_link_attributes:
-    - description="How to transfer files between devices using the NFC Android Beam feature."
+    path_attributes:
+    - name: description
+      value: How to transfer files between devices using the NFC Android Beam feature.
     section:
     - title: Sending Files to Another Device
       path: /training/beam-files/send-files.html
@@ -209,8 +292,9 @@
   section:
   - title: Managing Audio Playback
     path: /training/managing-audio/index.html
-    custom_link_attributes:
-    - description="How to respond to hardware audio key presses, request audio focus when playing audio, and respond appropriately to changes in audio focus."
+    path_attributes:
+    - name: description
+      value: How to respond to hardware audio key presses, request audio focus when playing audio, and respond appropriately to changes in audio focus.
     section:
     - title: Controlling Your App's Volume and Playback
       path: /training/managing-audio/volume-playback.html
@@ -220,8 +304,9 @@
       path: /training/managing-audio/audio-output.html
   - title: Capturing Photos
     path: /training/camera/index.html
-    custom_link_attributes:
-    - description="How to leverage existing camera apps on the user's device to capture photos or control the camera hardware directly and build your own camera app."
+    path_attributes:
+    - name: description
+      value: How to leverage existing camera apps on the user's device to capture photos or control the camera hardware directly and build your own camera app.
     section:
     - title: Taking Photos Simply
       path: /training/camera/photobasics.html
@@ -231,8 +316,9 @@
       path: /training/camera/cameradirect.html
   - title: Printing Content
     path: /training/printing/index.html
-    custom_link_attributes:
-    - description="How to print photos, HTML documents, and custom documents from your app."
+    path_attributes:
+    - name: description
+      value: How to print photos, HTML documents, and custom documents from your app.
     section:
     - title: Photos
       path: /training/printing/photos.html
@@ -246,8 +332,9 @@
   section:
   - title: Displaying Bitmaps Efficiently
     path: /training/displaying-bitmaps/index.html
-    custom_link_attributes:
-    - description="How to load and process bitmaps while keeping your user interface responsive and avoid exceeding memory limits."
+    path_attributes:
+    - name: description
+      value: How to load and process bitmaps while keeping your user interface responsive and avoid exceeding memory limits.
     section:
     - title: Loading Large Bitmaps Efficiently
       path: /training/displaying-bitmaps/load-bitmap.html
@@ -261,8 +348,9 @@
       path: /training/displaying-bitmaps/display-bitmap.html
   - title: Displaying Graphics with OpenGL ES
     path: /training/graphics/opengl/index.html
-    custom_link_attributes:
-    - description="How to create OpenGL graphics within the Android app framework and respond to touch input."
+    path_attributes:
+    - name: description
+      value: How to create OpenGL graphics within the Android app framework and respond to touch input.
     section:
     - title: Building an OpenGL ES Environment
       path: /training/graphics/opengl/environment.html
@@ -278,8 +366,9 @@
       path: /training/graphics/opengl/touch.html
   - title: Animating Views Using Scenes and Transitions
     path: /training/transitions/index.html
-    custom_link_attributes:
-    - description="How to animate state changes in a view hierarchy using transitions."
+    path_attributes:
+    - name: description
+      value: How to animate state changes in a view hierarchy using transitions.
     section:
     - title: The Transitions Framework
       path: /training/transitions/overview.html
@@ -291,8 +380,9 @@
       path: /training/transitions/custom-transitions.html
   - title: Adding Animations
     path: /training/animation/index.html
-    custom_link_attributes:
-    - description="How to add transitional animations to your user interface."
+    path_attributes:
+    - name: description
+      value: How to add transitional animations to your user interface.
     section:
     - title: Crossfading Two Views
       path: /training/animation/crossfade.html
@@ -310,8 +400,9 @@
   section:
   - title: Connecting Devices Wirelessly
     path: /training/connect-devices-wirelessly/index.html
-    custom_link_attributes:
-    - description="How to find and connect to local devices using Network Service Discovery and how to create peer-to-peer connections with Wi-Fi."
+    path_attributes:
+    - name: description
+      value: How to find and connect to local devices using Network Service Discovery and how to create peer-to-peer connections with Wi-Fi.
     section:
     - title: Using Network Service Discovery
       path: /training/connect-devices-wirelessly/nsd.html
@@ -321,8 +412,9 @@
       path: /training/connect-devices-wirelessly/nsd-wifi-direct.html
   - title: Performing Network Operations
     path: /training/basics/network-ops/index.html
-    custom_link_attributes:
-    - description="How to create a network connection, monitor the connection for changes in connectivity, and perform transactions with XML data."
+    path_attributes:
+    - name: description
+      value: How to create a network connection, monitor the connection for changes in connectivity, and perform transactions with XML data.
     section:
     - title: Connecting to the Network
       path: /training/basics/network-ops/connecting.html
@@ -332,8 +424,9 @@
       path: /training/basics/network-ops/xml.html
   - title: Transferring Data Without Draining the Battery
     path: /training/efficient-downloads/index.html
-    custom_link_attributes:
-    - description="How to minimize your app's impact on the battery when performing downloads and other network transactions."
+    path_attributes:
+    - name: description
+      value: How to minimize your app's impact on the battery when performing downloads and other network transactions.
     section:
     - title: Optimizing Downloads for Efficient Network Access
       path: /training/efficient-downloads/efficient-network-access.html
@@ -345,8 +438,9 @@
       path: /training/efficient-downloads/connectivity_patterns.html
   - title: Syncing to the Cloud
     path: /training/backup/index.html
-    custom_link_attributes:
-    - description="How to sync and back up app and user data to remote web services in the cloud and how to restore the data back to multiple devices."
+    path_attributes:
+    - name: description
+      value: How to sync and back up app and user data to remote web services in the cloud and how to restore the data back to multiple devices.
     section:
     - title: Configuring Auto Backup
       path: /training/backup/autosyncapi.html
@@ -354,12 +448,14 @@
       path: /training/backup/backupapi.html
   - title: Resolving Cloud Save Conflicts
     path: /training/cloudsave/conflict-res.html
-    custom_link_attributes:
-    - description="How to design a robust conflict resolution strategy for apps that save data to the cloud."
+    path_attributes:
+    - name: description
+      value: How to design a robust conflict resolution strategy for apps that save data to the cloud.
   - title: Transferring Data Using Sync Adapters
     path: /training/sync-adapters/index.html
-    custom_link_attributes:
-    - description="How to transfer data between the cloud and the device using the Android sync adapter framework"
+    path_attributes:
+    - name: description
+      value: How to transfer data between the cloud and the device using the Android sync adapter framework
     section:
     - title: Creating a Stub Authenticator
       path: /training/sync-adapters/creating-authenticator.html
@@ -371,8 +467,9 @@
       path: /training/sync-adapters/running-sync-adapter.html
   - title: Transmitting Network Data Using Volley
     path: /training/volley/index.html
-    custom_link_attributes:
-    - description="How to perform fast, scalable UI operations over the network using Volley"
+    path_attributes:
+    - name: description
+      value: How to perform fast, scalable UI operations over the network using Volley
     section:
     - title: Sending a Simple Request
       path: /training/volley/simple.html
@@ -388,8 +485,9 @@
   section:
   - title: Making Your App Location-Aware
     path: /training/location/index.html
-    custom_link_attributes:
-    - description="How to add location-aware features to your app by getting the user's current location."
+    path_attributes:
+    - name: description
+      value: How to add location-aware features to your app by getting the user's current location.
     section:
     - title: Getting the Last Known Location
       path: /training/location/retrieve-current.html
@@ -403,16 +501,18 @@
       path: /training/location/geofencing.html
   - title: Adding Maps
     path: /training/maps/index.html
-    custom_link_attributes:
-    - description="How to add maps and mapping information to your app."
+    path_attributes:
+    - name: description
+      value: How to add maps and mapping information to your app.
 
 - title: Building Apps with User Info & Sign-In
   path: /training/building-userinfo.html
   section:
   - title: Accessing Contacts Data
     path: /training/contacts-provider/index.html
-    custom_link_attributes:
-    - description="How to use Android's central address book, the Contacts Provider, to display contacts and their details and modify contact information."
+    path_attributes:
+    - name: description
+      value: How to use Android's central address book, the Contacts Provider, to display contacts and their details and modify contact information.
     section:
     - title: Retrieving a List of Contacts
       path: /training/contacts-provider/retrieve-names.html
@@ -424,16 +524,18 @@
       path: /training/contacts-provider/display-contact-badge.html
   - title: Adding Sign-In
     path: /training/sign-in/index.html
-    custom_link_attributes:
-    - description="How to add user sign-in functionality to your app."
+    path_attributes:
+    - name: description
+      value: How to add user sign-in functionality to your app.
 
 - title: Building Apps for Wearables
   path: /training/building-wearables.html
   section:
   - title: Adding Wearable Features to Notifications
     path: /training/wearables/notifications/index.html
-    custom_link_attributes:
-    - description="How to build handheld notifications that are synced to and look great on wearables."
+    path_attributes:
+    - name: description
+      value: How to build handheld notifications that are synced to and look great on wearables.
     section:
     - title: Creating a Notification
       path: /training/wearables/notifications/creating.html
@@ -445,8 +547,9 @@
       path: /training/wearables/notifications/stacks.html
   - title: Creating Wearable Apps
     path: /training/wearables/apps/index.html
-    custom_link_attributes:
-    - description="How to build apps that run directly on wearables."
+    path_attributes:
+    - name: description
+      value: How to build apps that run directly on wearables.
     section:
     - title: Creating and Running a Wearable App
       path: /training/wearables/apps/creating.html
@@ -462,8 +565,9 @@
       path: /training/wearables/apps/bt-debugging.html
   - title: Creating Custom UIs
     path: /training/wearables/ui/index.html
-    custom_link_attributes:
-    - description="How to create custom user interfaces for wearable apps."
+    path_attributes:
+    - name: description
+      value: How to create custom user interfaces for wearable apps.
     section:
     - title: Defining Layouts
       path: /training/wearables/ui/layouts.html
@@ -479,8 +583,9 @@
       path: /training/wearables/ui/exit.html
   - title: Sending and Syncing Data
     path: /training/wearables/data-layer/index.html
-    custom_link_attributes:
-    - description="How to sync data between handhelds and wearables."
+    path_attributes:
+    - name: description
+      value: How to sync data between handhelds and wearables.
     section:
     - title: Accessing the Wearable Data Layer
       path: /training/wearables/data-layer/accessing.html
@@ -494,8 +599,9 @@
       path: /training/wearables/data-layer/events.html
   - title: Creating Watch Faces
     path: /training/wearables/watch-faces/index.html
-    custom_link_attributes:
-    - description="How to create watch faces for wearables."
+    path_attributes:
+    - name: description
+      value: How to create watch faces for wearables.
     section:
     - title: Designing Watch Faces
       path: /training/wearables/watch-faces/designing.html
@@ -515,70 +621,85 @@
       path: /training/wearables/watch-faces/performance.html
   - title: Detecting Location
     path: /training/articles/wear-location-detection.html
-    custom_link_attributes:
-    - description="How to detect location data on Android Wear devices."
+    path_attributes:
+    - name: description
+      value: How to detect location data on Android Wear devices.
   - title: Requesting Permissions
     path: /training/articles/wear-permissions.html
-    custom_link_attributes:
-    - description="How to request permissions on Android Wear devices."
+    path_attributes:
+    - name: description
+      value: How to request permissions on Android Wear devices.
   - title: Using the Speaker
     path: /training/wearables/wearable-sounds.html
-    custom_link_attributes:
-    - description="How to use the speaker on Android Wear devices."
+    path_attributes:
+    - name: description
+      value: How to use the speaker on Android Wear devices.
 
 - title: Building Apps for TV
   path: /training/tv/index.html
   section:
   - title: Building TV Apps
     path: /training/tv/start/index.html
-    custom_link_attributes:
-    - ja-lang="TV アプリのビルド"
-    - description="How to start building TV apps or extend your existing app to run on TV devices."
+    path_attributes:
+    - name: ja-lang
+      value: TV アプリのビルド
+    - name: description
+      value: How to start building TV apps or extend your existing app to run on TV devices.
     section:
     - title: Getting Started with TV Apps
       path: /training/tv/start/start.html
-      custom_link_attributes:
-      - ja-lang="TV アプリのビルドを開始する"
+      path_attributes:
+      - name: ja-lang
+        value: TV アプリのビルドを開始する
     - title: Handling TV Hardware
       path: /training/tv/start/hardware.html
-      custom_link_attributes:
-      - ja-lang="TV ハードウェアを処理する"
+      path_attributes:
+      - name: ja-lang
+        value: TV ハードウェアを処理する
     - title: Building TV Layouts
       path: /training/tv/start/layouts.html
-      custom_link_attributes:
-      - ja-lang="TV 向けレイアウトをビルドする"
+      path_attributes:
+      - name: ja-lang
+        value: TV 向けレイアウトをビルドする
     - title: Creating TV Navigation
       path: /training/tv/start/navigation.html
-      custom_link_attributes:
-      - ja-lang="TV 用のナビゲーションを作成する"
+      path_attributes:
+      - name: ja-lang
+        value: TV 用のナビゲーションを作成する
   - title: Building TV Playback Apps
     path: /training/tv/playback/index.html
-    custom_link_attributes:
-    - ja-lang="TV 再生アプリのビルド"
-    - description="How to build apps that provide media catalogs and play content."
+    path_attributes:
+    - name: ja-lang
+      value: TV 再生アプリのビルド
+    - name: description
+      value: How to build apps that provide media catalogs and play content.
     section:
     - title: Creating a Catalog Browser
       path: /training/tv/playback/browse.html
-      custom_link_attributes:
-      - ja-lang="カタログ ブラウザを作成する"
+      path_attributes:
+      - name: ja-lang
+        value: カタログ ブラウザを作成する
     - title: Providing a Card View
       path: /training/tv/playback/card.html
     - title: Building a Details View
       path: /training/tv/playback/details.html
-      custom_link_attributes:
-      - ja-lang="詳細ビューをビルドする"
+      path_attributes:
+      - name: ja-lang
+        value: 詳細ビューをビルドする
     - title: Displaying a Now Playing Card
       path: /training/tv/playback/now-playing.html
-      custom_link_attributes:
-      - ja-lang="再生中カードを表示する"
+      path_attributes:
+      - name: ja-lang
+        value: 再生中カードを表示する
     - title: Adding a Guided Step
       path: /training/tv/playback/guided-step.html
     - title: Enabling Background Playback
       path: /training/tv/playback/options.html
   - title: Helping Users Find Content on TV
     path: /training/tv/discovery/index.html
-    custom_link_attributes:
-    - description="How to help users discover content from your app."
+    path_attributes:
+    - name: description
+      value: How to help users discover content from your app.
     section:
     - title: Recommending TV Content
       path: /training/tv/discovery/recommendations.html
@@ -588,12 +709,14 @@
       path: /training/tv/discovery/in-app-search.html
   - title: Building TV Games
     path: /training/tv/games/index.html
-    custom_link_attributes:
-    - description="How to build games for TV."
+    path_attributes:
+    - name: description
+      value: How to build games for TV.
   - title: Building TV Channels
     path: /training/tv/tif/index.html
-    custom_link_attributes:
-    - description="How to build channels for TV."
+    path_attributes:
+    - name: description
+      value: How to build channels for TV.
     section:
     - title: Developing a TV Input Service
       path: /training/tv/tif/tvinput.html
@@ -603,24 +726,28 @@
       path: /training/tv/tif/ui.html
   - title: TV Apps Checklist
     path: /training/tv/publishing/checklist.html
-    custom_link_attributes:
-    - description="An itemized list of requirements for TV apps."
+    path_attributes:
+    - name: description
+      value: An itemized list of requirements for TV apps.
 
 - title: Building Apps for Auto
   path: /training/auto/index.html
   section:
   - title: Getting Started with Auto
     path: /training/auto/start/index.html
-    custom_link_attributes:
-    - description="How to start building or extending apps that work with Auto devices."
+    path_attributes:
+    - name: description
+      value: How to start building or extending apps that work with Auto devices.
   - title: Playing Audio for Auto
     path: /training/auto/audio/index.html
-    custom_link_attributes:
-    - description="How to extend audio apps to play content on Auto devices."
+    path_attributes:
+    - name: description
+      value: How to extend audio apps to play content on Auto devices.
   - title: Messaging for Auto
     path: /training/auto/messaging/index.html
-    custom_link_attributes:
-    - description="How to extend text messaging apps to work with Auto devices."
+    path_attributes:
+    - name: description
+      value: How to extend text messaging apps to work with Auto devices.
 
 - title: Building Apps for Work
   path: /training/enterprise/index.html
@@ -639,8 +766,9 @@
   section:
   - title: Designing Effective Navigation
     path: /training/design-navigation/index.html
-    custom_link_attributes:
-    - description="How to plan your app's screen hierarchy and forms of navigation so users can effectively and intuitively traverse your app content using various navigation patterns."
+    path_attributes:
+    - name: description
+      value: How to plan your app's screen hierarchy and forms of navigation so users can effectively and intuitively traverse your app content using various navigation patterns.
     section:
     - title: Planning Screens and Their Relationships
       path: /training/design-navigation/screen-planning.html
@@ -654,8 +782,9 @@
       path: /training/design-navigation/wireframing.html
   - title: Implementing Effective Navigation
     path: /training/implementing-navigation/index.html
-    custom_link_attributes:
-    - description="How to implement various navigation patterns such as swipe views, a navigation drawer, and up navigation."
+    path_attributes:
+    - name: description
+      value: How to implement various navigation patterns such as swipe views, a navigation drawer, and up navigation.
     section:
     - title: Creating Swipe Views with Tabs
       path: /training/implementing-navigation/lateral.html
@@ -669,8 +798,9 @@
       path: /training/implementing-navigation/descendant.html
   - title: Notifying the User
     path: /training/notify-user/index.html
-    custom_link_attributes:
-    - description="How to display messages called notifications outside of your application's UI."
+    path_attributes:
+    - name: description
+      value: How to display messages called notifications outside of your application's UI.
     section:
     - title: Building a Notification
       path: /training/notify-user/build-notification.html
@@ -684,8 +814,9 @@
       path: /training/notify-user/display-progress.html
   - title: Supporting Swipe-to-Refresh
     path: /training/swipe/index.html
-    custom_link_attributes:
-    - description="How to modify your app's layout to support manual content updates triggered by the swipe-to-refresh gesture."
+    path_attributes:
+    - name: description
+      value: How to modify your app's layout to support manual content updates triggered by the swipe-to-refresh gesture.
     section:
     - title: Adding Swipe-to-Refresh To Your App
       path: /training/swipe/add-swipe-interface.html
@@ -693,8 +824,9 @@
       path: /training/swipe/respond-refresh-request.html
   - title: Adding Search Functionality
     path: /training/search/index.html
-    custom_link_attributes:
-    - description="How to properly add a search interface to your app and create a searchable database."
+    path_attributes:
+    - name: description
+      value: How to properly add a search interface to your app and create a searchable database.
     section:
     - title: Setting up the Search Interface
       path: /training/search/setup.html
@@ -704,8 +836,9 @@
       path: /training/search/backward-compat.html
   - title: Making Your App Content Searchable by Google
     path: /training/app-indexing/index.html
-    custom_link_attributes:
-    - description="How to enable deep linking and indexing of your application content so that users can open this content directly from their mobile search results."
+    path_attributes:
+    - name: description
+      value: How to enable deep linking and indexing of your application content so that users can open this content directly from their mobile search results.
     section:
     - title: Enabling Deep Links for App Content
       path: /training/app-indexing/deep-linking.html
@@ -713,47 +846,64 @@
       path: /training/app-indexing/enabling-app-indexing.html
   - title: Optimizing Content for the Assistant
     path: /training/articles/assistant.html
-    custom_link_attributes:
-    - description="Support contextually relevant actions through the Assist API."
+    path_attributes:
+    - name: description
+      value: Support contextually relevant actions through the Assist API.
   - title: Handling App Links
     path: /training/app-links/index.html
-    custom_link_attributes:
-    - description="How to enable the system to handle web requests by taking the user directly to your app instead of your website."
+    path_attributes:
+    - name: description
+      value: How to enable the system to handle web requests by taking the user directly to your app instead of your website.
 
 - title: Best Practices for User Interface
   path: /training/best-ui.html
   section:
   - title: Designing for Multiple Screens
     path: /training/multiscreen/index.html
-    custom_link_attributes:
-    - es-lang="Cómo diseñar aplicaciones para varias pantallas"
-    - ja-lang="複数画面のデザイン"
-    - zh-cn-lang="针对多种屏幕进行设计"
-    - description="How to build a user interface that's flexible enough to fit perfectly on any screen and how to create different interaction patterns that are optimized for different screen sizes."
+    path_attributes:
+    - name: es-lang
+      value: Cómo diseñar aplicaciones para varias pantallas
+    - name: ja-lang
+      value: 複数画面のデザイン
+    - name: zh-cn-lang
+      value: 针对多种屏幕进行设计
+    - name: description
+      value: How to build a user interface that's flexible enough to fit perfectly on any screen and how to create different interaction patterns that are optimized for different screen sizes.
     section:
     - title: Supporting Different Screen Sizes
       path: /training/multiscreen/screensizes.html
-      custom_link_attributes:
-      - es-lang="Cómo admitir varios tamaños de pantalla"
-      - ja-lang="さまざまな画面サイズのサポート"
-      - ko-lang="다양한 화면 크기 지원"
-      - zh-cn-lang="支持各种屏幕尺寸"
+      path_attributes:
+      - name: es-lang
+        value: Cómo admitir varios tamaños de pantalla
+      - name: ja-lang
+        value: さまざまな画面サイズのサポート
+      - name: ko-lang
+        value: 다양한 화면 크기 지원
+      - name: zh-cn-lang
+        value: 支持各种屏幕尺寸
     - title: Supporting Different Screen Densities
       path: /training/multiscreen/screendensities.html
-      custom_link_attributes:
-      - es-lang="Cómo admitir varias densidades de pantalla"
-      - ja-lang="さまざまな画面密度のサポート"
-      - zh-cn-lang="支持各种屏幕密度"
+      path_attributes:
+      - name: es-lang
+        value: Cómo admitir varias densidades de pantalla
+      - name: ja-lang
+        value: さまざまな画面密度のサポート
+      - name: zh-cn-lang
+        value: 支持各种屏幕密度
     - title: Implementing Adaptive UI Flows
       path: /training/multiscreen/adaptui.html
-      custom_link_attributes:
-      - es-lang="Cómo implementar interfaces de usuario adaptables"
-      - ja-lang="順応性のある UI フローの実装"
-      - zh-cn-lang="实施自适应用户界面流程"
+      path_attributes:
+      - name: es-lang
+        value: Cómo implementar interfaces de usuario adaptables
+      - name: ja-lang
+        value: 順応性のある UI フローの実装
+      - name: zh-cn-lang
+        value: 实施自适应用户界面流程
   - title: Adding the App Bar
     path: /training/appbar/index.html
-    custom_link_attributes:
-    - description="How to use the support library's toolbar widget to implement an app bar that displays properly on a wide range of devices."
+    path_attributes:
+    - name: description
+      value: How to use the support library's toolbar widget to implement an app bar that displays properly on a wide range of devices.
     section:
     - title: Setting Up the App Bar
       path: /training/appbar/setting-up.html
@@ -765,8 +915,9 @@
       path: /training/appbar/action-views.html
   - title: Showing Pop-Up Messages
     path: /training/snackbar/index.html
-    custom_link_attributes:
-    - description="How to use the support library's Snackbar widget to display a brief pop-up message."
+    path_attributes:
+    - name: description
+      value: How to use the support library's Snackbar widget to display a brief pop-up message.
     section:
     - title: Building and Displaying a Pop-Up Message
       path: /training/snackbar/showing.html
@@ -774,8 +925,9 @@
       path: /training/snackbar/action.html
   - title: Creating Custom Views
     path: /training/custom-views/index.html
-    custom_link_attributes:
-    - description="How to build custom UI widgets that are interactive and smooth."
+    path_attributes:
+    - name: description
+      value: How to build custom UI widgets that are interactive and smooth.
     section:
     - title: Creating a Custom View Class
       path: /training/custom-views/create-view.html
@@ -787,8 +939,9 @@
       path: /training/custom-views/optimizing-view.html
   - title: Creating Backward-Compatible UIs
     path: /training/backward-compatible-ui/index.html
-    custom_link_attributes:
-    - description="How to use UI components and other APIs from the more recent versions of Android while remaining compatible with older versions of the platform."
+    path_attributes:
+    - name: description
+      value: How to use UI components and other APIs from the more recent versions of Android while remaining compatible with older versions of the platform.
     section:
     - title: Abstracting the New APIs
       path: /training/backward-compatible-ui/abstracting.html
@@ -800,8 +953,9 @@
       path: /training/backward-compatible-ui/using-component.html
   - title: Implementing Accessibility
     path: /training/accessibility/index.html
-    custom_link_attributes:
-    - description="How to make your app accessible to users with vision impairment or other physical disabilities."
+    path_attributes:
+    - name: description
+      value: How to make your app accessible to users with vision impairment or other physical disabilities.
     section:
     - title: Developing Accessible Applications
       path: /training/accessibility/accessible-app.html
@@ -811,8 +965,9 @@
       path: /training/accessibility/testing.html
   - title: Managing the System UI
     path: /training/system-ui/index.html
-    custom_link_attributes:
-    - description="How to hide and show status and navigation bars across different versions of Android, while managing the display of other screen components."
+    path_attributes:
+    - name: description
+      value: How to hide and show status and navigation bars across different versions of Android, while managing the display of other screen components.
     section:
     - title: Dimming the System Bars
       path: /training/system-ui/dim.html
@@ -826,110 +981,184 @@
       path: /training/system-ui/visibility.html
   - title: Creating Apps with Material Design
     path: /training/material/index.html
-    custom_link_attributes:
-    - es-lang="Crear aplicaciones con Material Design"
-    - in-lang="Desain Bahan untuk Pengembang"
-    - ja-lang="マテリアル デザインでのアプリ作成"
-    - ko-lang="개발자를 위한 머티리얼 디자인"
-    - pt-br-lang="Material Design para desenvolvedores"
-    - ru-lang="Создание приложений с помощью Material Design"
-    - vi-lang="Material Design cho Nhà phát triển"
-    - zh-cn-lang="面向开发者的材料设计"
-    - zh-tw-lang="開發人員材料設計"
-    - description="How to implement material design on Android."
+    path_attributes:
+    - name: es-lang
+      value: Crear aplicaciones con Material Design
+    - name: in-lang
+      value: Desain Bahan untuk Pengembang
+    - name: ja-lang
+      value: マテリアル デザインでのアプリ作成
+    - name: ko-lang
+      value: 개발자를 위한 머티리얼 디자인
+    - name: pt-br-lang
+      value: Material Design para desenvolvedores
+    - name: ru-lang
+      value: Создание приложений с помощью Material Design
+    - name: vi-lang
+      value: Material Design cho Nhà phát triển
+    - name: zh-cn-lang
+      value: 面向开发者的材料设计
+    - name: zh-tw-lang
+      value: 開發人員材料設計
+    - name: description
+      value: How to implement material design on Android.
     section:
     - title: Getting Started
       path: /training/material/get-started.html
-      custom_link_attributes:
-      - es-lang="Comencemos"
-      - in-lang="Memulai"
-      - ja-lang="スタート ガイド"
-      - ko-lang="시작하기"
-      - pt-br-lang="Como iniciar"
-      - ru-lang="Начало работы"
-      - vi-lang="Bắt đầu"
-      - zh-cn-lang="入门指南"
-      - zh-tw-lang="開始使用"
+      path_attributes:
+      - name: es-lang
+        value: Comencemos
+      - name: in-lang
+        value: Memulai
+      - name: ja-lang
+        value: スタート ガイド
+      - name: ko-lang
+        value: 시작하기
+      - name: pt-br-lang
+        value: Como iniciar
+      - name: ru-lang
+        value: Начало работы
+      - name: vi-lang
+        value: Bắt đầu
+      - name: zh-cn-lang
+        value: 入门指南
+      - name: zh-tw-lang
+        value: 開始使用
     - title: Using the Material Theme
       path: /training/material/theme.html
-      custom_link_attributes:
-      - es-lang="Usar el tema Material"
-      - in-lang="Menggunakan Tema Bahan"
-      - ja-lang="マテリアル テーマの使用"
-      - ko-lang="머티어리얼 테마 사용"
-      - pt-br-lang="Como usar o tema do Material"
-      - ru-lang="Использование темы Material Design"
-      - vi-lang="Sử dụng Chủ đề Material"
-      - zh-cn-lang="使用材料主题"
-      - zh-tw-lang="使用材料設計風格"
+      path_attributes:
+      - name: es-lang
+        value: Usar el tema Material
+      - name: in-lang
+        value: Menggunakan Tema Bahan
+      - name: ja-lang
+        value: マテリアル テーマの使用
+      - name: ko-lang
+        value: 머티어리얼 테마 사용
+      - name: pt-br-lang
+        value: Como usar o tema do Material
+      - name: ru-lang
+        value: Использование темы Material Design
+      - name: vi-lang
+        value: Sử dụng Chủ đề Material
+      - name: zh-cn-lang
+        value: 使用材料主题
+      - name: zh-tw-lang
+        value: 使用材料設計風格
     - title: Creating Lists and Cards
       path: /training/material/lists-cards.html
-      custom_link_attributes:
-      - es-lang="Crear listas y tarjetas"
-      - in-lang="Membuat Daftar dan Kartu"
-      - ja-lang="リストとカードの作成"
-      - ko-lang="목록 및 카드 생성"
-      - pt-br-lang="Como criar listas e cartões"
-      - ru-lang="Создание списков и подсказок"
-      - vi-lang="Tạo Danh sách và Thẻ"
-      - zh-cn-lang="创建列表与卡片"
-      - zh-tw-lang="建立清單和卡片"
+      path_attributes:
+      - name: es-lang
+        value: Crear listas y tarjetas
+      - name: in-lang
+        value: Membuat Daftar dan Kartu
+      - name: ja-lang
+        value: リストとカードの作成
+      - name: ko-lang
+        value: 목록 및 카드 생성
+      - name: pt-br-lang
+        value: Como criar listas e cartões
+      - name: ru-lang
+        value: Создание списков и подсказок
+      - name: vi-lang
+        value: Tạo Danh sách và Thẻ
+      - name: zh-cn-lang
+        value: 创建列表与卡片
+      - name: zh-tw-lang
+        value: 建立清單和卡片
     - title: Defining Shadows and Clipping Views
       path: /training/material/shadows-clipping.html
-      custom_link_attributes:
-      - es-lang="Definir vistas de recorte y sombras"
-      - in-lang="Mendefinisikan Bayangan dan Memangkas Tampilan"
-      - ja-lang="シャドウとクリッピング ビューの定義"
-      - ko-lang="그림자 정의 및 뷰 클리핑"
-      - pt-br-lang="Como definir sombras e recortar visualizações"
-      - ru-lang="Определение теней и обрезка представлений"
-      - vi-lang="Định nghĩa Đổ bóng và Dạng xem Cắt hình"
-      - zh-cn-lang="定义阴影与裁剪视图"
-      - zh-tw-lang="定義陰影和裁剪檢視"
+      path_attributes:
+      - name: es-lang
+        value: Definir vistas de recorte y sombras
+      - name: in-lang
+        value: Mendefinisikan Bayangan dan Memangkas Tampilan
+      - name: ja-lang
+        value: シャドウとクリッピング ビューの定義
+      - name: ko-lang
+        value: 그림자 정의 및 뷰 클리핑
+      - name: pt-br-lang
+        value: Como definir sombras e recortar visualizações
+      - name: ru-lang
+        value: Определение теней и обрезка представлений
+      - name: vi-lang
+        value: Định nghĩa Đổ bóng và Dạng xem Cắt hình
+      - name: zh-cn-lang
+        value: 定义阴影与裁剪视图
+      - name: zh-tw-lang
+        value: 定義陰影和裁剪檢視
     - title: Working with Drawables
       path: /training/material/drawables.html
-      custom_link_attributes:
-      - es-lang="Trabajar con interfaces dibujables"
-      - in-lang="Bekerja dengan Drawable"
-      - ja-lang="ドローアブルの使用"
-      - ko-lang="Drawable 사용"
-      - pt-br-lang="Como trabalhar com desenháveis"
-      - ru-lang="Работа с элементами дизайна"
-      - vi-lang="Làm việc với Nội dung vẽ được"
-      - zh-cn-lang="使用 Drawables"
-      - zh-tw-lang="使用可繪項目"
+      path_attributes:
+      - name: es-lang
+        value: Trabajar con interfaces dibujables
+      - name: in-lang
+        value: Bekerja dengan Drawable
+      - name: ja-lang
+        value: ドローアブルの使用
+      - name: ko-lang
+        value: Drawable 사용
+      - name: pt-br-lang
+        value: Como trabalhar com desenháveis
+      - name: ru-lang
+        value: Работа с элементами дизайна
+      - name: vi-lang
+        value: Làm việc với Nội dung vẽ được
+      - name: zh-cn-lang
+        value: 使用 Drawables
+      - name: zh-tw-lang
+        value: 使用可繪項目
     - title: Defining Custom Animations
       path: /training/material/animations.html
-      custom_link_attributes:
-      - es-lang="Definir animaciones personalizadas"
-      - in-lang="Mendefinisikan Animasi Custom"
-      - ja-lang="カスタム アニメーションの定義"
-      - ko-lang="사용자지정 애니메이션 정의"
-      - pt-br-lang="Como definir animações personalizadas"
-      - ru-lang="Определение настраиваемой анимации"
-      - vi-lang="Định nghĩa Hoạt hình Tùy chỉnh"
-      - zh-cn-lang="定义定制动画"
-      - zh-tw-lang="定義自訂動畫"
+      path_attributes:
+      - name: es-lang
+        value: Definir animaciones personalizadas
+      - name: in-lang
+        value: Mendefinisikan Animasi Custom
+      - name: ja-lang
+        value: カスタム アニメーションの定義
+      - name: ko-lang
+        value: 사용자지정 애니메이션 정의
+      - name: pt-br-lang
+        value: Como definir animações personalizadas
+      - name: ru-lang
+        value: Определение настраиваемой анимации
+      - name: vi-lang
+        value: Định nghĩa Hoạt hình Tùy chỉnh
+      - name: zh-cn-lang
+        value: 定义定制动画
+      - name: zh-tw-lang
+        value: 定義自訂動畫
     - title: Maintaining Compatibility
       path: /training/material/compatibility.html
-      custom_link_attributes:
-      - es-lang="Mantener la compatibilidad"
-      - in-lang="Mempertahankan Kompatibilitas"
-      - ja-lang="互換性の維持"
-      - ko-lang="호환성 유지"
-      - pt-br-lang="Como manter a compatibilidade"
-      - ru-lang="Обеспечение совместимости"
-      - vi-lang="Duy trì Tính tương thích"
-      - zh-cn-lang="维护兼容性"
-      - zh-tw-lang="維持相容性"
+      path_attributes:
+      - name: es-lang
+        value: Mantener la compatibilidad
+      - name: in-lang
+        value: Mempertahankan Kompatibilitas
+      - name: ja-lang
+        value: 互換性の維持
+      - name: ko-lang
+        value: 호환성 유지
+      - name: pt-br-lang
+        value: Como manter a compatibilidade
+      - name: ru-lang
+        value: Обеспечение совместимости
+      - name: vi-lang
+        value: Duy trì Tính tương thích
+      - name: zh-cn-lang
+        value: 维护兼容性
+      - name: zh-tw-lang
+        value: 維持相容性
 
 - title: Best Practices for User Input
   path: /training/best-user-input.html
   section:
   - title: Using Touch Gestures
     path: /training/gestures/index.html
-    custom_link_attributes:
-    - description="How to write apps that allow users to interact with the touch screen via touch gestures."
+    path_attributes:
+    - name: description
+      value: How to write apps that allow users to interact with the touch screen via touch gestures.
     section:
     - title: Detecting Common Gestures
       path: /training/gestures/detector.html
@@ -945,8 +1174,9 @@
       path: /training/gestures/viewgroup.html
   - title: Handling Keyboard Input
     path: /training/keyboard-input/index.html
-    custom_link_attributes:
-    - description="How to specify the appearance and behaviors of soft input methods (such as on-screen keyboards) and how to optimize the experience with hardware keyboards."
+    path_attributes:
+    - name: description
+      value: How to specify the appearance and behaviors of soft input methods (such as on-screen keyboards) and how to optimize the experience with hardware keyboards.
     section:
     - title: Specifying the Input Method Type
       path: /training/keyboard-input/style.html
@@ -958,8 +1188,9 @@
       path: /training/keyboard-input/commands.html
   - title: Supporting Game Controllers
     path: /training/game-controllers/index.html
-    custom_link_attributes:
-    - description="How to write apps that support game controllers."
+    path_attributes:
+    - name: description
+      value: How to write apps that support game controllers.
     section:
     - title: Handling Controller Actions
       path: /training/game-controllers/controller-input.html
@@ -973,8 +1204,9 @@
   section:
   - title: Running in a Background Service
     path: /training/run-background-service/index.html
-    custom_link_attributes:
-    - description="How to improve UI performance and responsiveness by sending work to a Service running in the background"
+    path_attributes:
+    - name: description
+      value: How to improve UI performance and responsiveness by sending work to a Service running in the background
     section:
     - title: Creating a Background Service
       path: /training/run-background-service/create-service.html
@@ -984,8 +1216,9 @@
       path: /training/run-background-service/report-status.html
   - title: Loading Data in the Background
     path: /training/load-data-background/index.html
-    custom_link_attributes:
-    - description="How to use CursorLoader to query data without affecting UI responsiveness."
+    path_attributes:
+    - name: description
+      value: How to use CursorLoader to query data without affecting UI responsiveness.
     section:
     - title: Running a Query with a CursorLoader
       path: /training/load-data-background/setup-loader.html
@@ -993,8 +1226,9 @@
       path: /training/load-data-background/handle-results.html
   - title: Managing Device Awake State
     path: /training/scheduling/index.html
-    custom_link_attributes:
-    - description="How to use repeating alarms and wake locks to run background jobs."
+    path_attributes:
+    - name: description
+      value: How to use repeating alarms and wake locks to run background jobs.
     section:
     - title: Keeping the Device Awake
       path: /training/scheduling/wakelock.html
@@ -1006,16 +1240,19 @@
   section:
   - title: Managing Your App's Memory
     path: /training/articles/memory.html
-    custom_link_attributes:
-    - description="How to keep your app's memory footprint small in order to improve performance on a variety of mobile devices."
+    path_attributes:
+    - name: description
+      value: How to keep your app's memory footprint small in order to improve performance on a variety of mobile devices.
   - title: Performance Tips
     path: /training/articles/perf-tips.html
-    custom_link_attributes:
-    - description="How to optimize your app's performance in various ways to improve its responsiveness and battery efficiency."
+    path_attributes:
+    - name: description
+      value: How to optimize your app's performance in various ways to improve its responsiveness and battery efficiency.
   - title: Improving Layout Performance
     path: /training/improving-layouts/index.html
-    custom_link_attributes:
-    - description="How to identify problems in your app's layout performance and improve the UI responsiveness."
+    path_attributes:
+    - name: description
+      value: How to identify problems in your app's layout performance and improve the UI responsiveness.
     section:
     - title: Optimizing Layout Hierarchies
       path: /training/improving-layouts/optimizing-layout.html
@@ -1027,11 +1264,15 @@
       path: /training/improving-layouts/smooth-scrolling.html
   - title: Optimizing Battery Life
     path: /training/monitoring-device-state/index.html
-    custom_link_attributes:
-    - es-lang="Cómo optimizar la duración de la batería"
-    - ja-lang="電池消費量の最適化"
-    - zh-cn-lang="优化电池使用时间"
-    - description="How to minimize the amount of power your app requires by adapting to current power conditions and performing power-hungry tasks at proper intervals."
+    path_attributes:
+    - name: es-lang
+      value: Cómo optimizar la duración de la batería
+    - name: ja-lang
+      value: 電池消費量の最適化
+    - name: zh-cn-lang
+      value: 优化电池使用时间
+    - name: description
+      value: How to minimize the amount of power your app requires by adapting to current power conditions and performing power-hungry tasks at proper intervals.
     section:
     - title: Reducing Network Battery Drain
       path: /training/performance/battery/network/index.html
@@ -1052,32 +1293,45 @@
       path: /training/monitoring-device-state/doze-standby.html
     - title: Monitoring the Battery Level and Charging State
       path: /training/monitoring-device-state/battery-monitoring.html
-      custom_link_attributes:
-      - es-lang="Cómo controlar el nivel de batería y el estado de carga"
-      - ja-lang="電池残量と充電状態の監視"
-      - zh-cn-lang="监控电池电量和充电状态"
+      path_attributes:
+      - name: es-lang
+        value: Cómo controlar el nivel de batería y el estado de carga
+      - name: ja-lang
+        value: 電池残量と充電状態の監視
+      - name: zh-cn-lang
+        value: 监控电池电量和充电状态
     - title: Determining and Monitoring the Docking State and Type
       path: /training/monitoring-device-state/docking-monitoring.html
-      custom_link_attributes:
-      - es-lang="Cómo determinar y controlar el tipo de conector y el estado de la conexión"
-      - ja-lang="ホルダーの装着状態とタイプの特定と監視"
-      - zh-cn-lang="确定和监控基座对接状态和类型"
+      path_attributes:
+      - name: es-lang
+        value: Cómo determinar y controlar el tipo de conector y el estado de la conexión
+      - name: ja-lang
+        value: ホルダーの装着状態とタイプの特定と監視
+      - name: zh-cn-lang
+        value: 确定和监控基座对接状态和类型
     - title: Determining and Monitoring the Connectivity Status
       path: /training/monitoring-device-state/connectivity-monitoring.html
-      custom_link_attributes:
-      - es-lang="Cómo determinar y controlar el estado de la conectividad"
-      - ja-lang="接続状態の特定と監視"
-      - zh-cn-lang="确定和监控网络连接状态"
+      path_attributes:
+      - name: es-lang
+        value: Cómo determinar y controlar el estado de la conectividad
+      - name: ja-lang
+        value: 接続状態の特定と監視
+      - name: zh-cn-lang
+        value: 确定和监控网络连接状态
     - title: Manipulating Broadcast Receivers On Demand
       path: /training/monitoring-device-state/manifest-receivers.html
-      custom_link_attributes:
-      - es-lang="Cómo manipular los receptores de emisión bajo demanda"
-      - ja-lang="オンデマンドでのブロードキャスト レシーバ操作"
-      - zh-cn-lang="根据需要操作广播接收器"
+      path_attributes:
+      - name: es-lang
+        value: Cómo manipular los receptores de emisión bajo demanda
+      - name: ja-lang
+        value: オンデマンドでのブロードキャスト レシーバ操作
+      - name: zh-cn-lang
+        value: 根据需要操作广播接收器
   - title: Sending Operations to Multiple Threads
     path: /training/multiple-threads/index.html
-    custom_link_attributes:
-    - description="How to improve the performance and scalability of long-running operations by dispatching work to multiple threads."
+    path_attributes:
+    - name: description
+      value: How to improve the performance and scalability of long-running operations by dispatching work to multiple threads.
     section:
     - title: Specifying the Code to Run on a Thread
       path: /training/multiple-threads/define-runnable.html
@@ -1089,68 +1343,81 @@
       path: /training/multiple-threads/communicate-ui.html
   - title: Keeping Your App Responsive
     path: /training/articles/perf-anr.html
-    custom_link_attributes:
-    - description="How to keep your app responsive to user interaction so the UI does not lock-up and display an \"Application Not Responding\" dialog."
+    path_attributes:
+    - name: description
+      value: How to keep your app responsive to user interaction so the UI does not lock-up and display an "Application Not Responding" dialog.
   - title: JNI Tips
     path: /training/articles/perf-jni.html
-    custom_link_attributes:
-    - description="How to efficiently use the Java Native Interface with the Android NDK."
+    path_attributes:
+    - name: description
+      value: How to efficiently use the Java Native Interface with the Android NDK.
   - title: SMP Primer for Android
     path: /training/articles/smp.html
-    custom_link_attributes:
-    - description="Tips for coding Android apps on symmetric multiprocessor systems."
+    path_attributes:
+    - name: description
+      value: Tips for coding Android apps on symmetric multiprocessor systems.
 
 - title: Best Practices for Security & Privacy
   path: /training/best-security.html
   section:
   - title: Security Tips
     path: /training/articles/security-tips.html
-    custom_link_attributes:
-    - description="How to perform various tasks and keep your app's data and your user's data secure."
+    path_attributes:
+    - name: description
+      value: How to perform various tasks and keep your app's data and your user's data secure.
   - title: Security with HTTPS and SSL
     path: /training/articles/security-ssl.html
-    custom_link_attributes:
-    - description="How to ensure that your app is secure when performing network transactions."
+    path_attributes:
+    - name: description
+      value: How to ensure that your app is secure when performing network transactions.
   - title: Updating Your Security Provider to Protect Against SSL Exploits
     path: /training/articles/security-gms-provider.html
-    custom_link_attributes:
-    - description="How to use and update Google Play services security provider, to protect against SSL exploits."
+    path_attributes:
+    - name: description
+      value: How to use and update Google Play services security provider, to protect against SSL exploits.
   - title: Checking Device Compatibility with SafetyNet
     path: /training/safetynet/index.html
-    custom_link_attributes:
-    - description="How to use the SafetyNet service to analyze a device where your app is running and get information about its compatibility with your app."
+    path_attributes:
+    - name: description
+      value: How to use the SafetyNet service to analyze a device where your app is running and get information about its compatibility with your app.
   - title: Enhancing Security with Device Management Policies
     path: /training/enterprise/device-management-policy.html
-    custom_link_attributes:
-    - description="How to create an application that enforces security policies on devices."
+    path_attributes:
+    - name: description
+      value: How to create an application that enforces security policies on devices.
 
 - title: Best Practices for Permissions & Identifiers
   path: /training/best-permissions-ids.html
   section:
   - title: Permissions and User Data
     path: /training/articles/user-data-overview.html
-    custom_link_attributes:
-    - description="Overview of app permissions on Android and how they affect your users."
+    path_attributes:
+    - name: description
+      value: Overview of app permissions on Android and how they affect your users.
   - title: Best Practices for App Permissions
     path: /training/articles/user-data-permissions.html
-    custom_link_attributes:
-    - description="How to manage permissions the right way for users."
+    path_attributes:
+    - name: description
+      value: How to manage permissions the right way for users.
   - title: Best Practices for Unique Identifiers
     path: /training/articles/user-data-ids.html
-    custom_link_attributes:
-    - description="Unique identifiers available and how to choose the right one for your use case."
+    path_attributes:
+    - name: description
+      value: Unique identifiers available and how to choose the right one for your use case.
 
 - title: Best Practices for Testing
   path: /training/testing/index.html
   section:
   - title: Getting Started with Testing
     path: /training/testing/start/index.html
-    custom_link_attributes:
-    - description="How to get started with testing your Android applications."
+    path_attributes:
+    - name: description
+      value: How to get started with testing your Android applications.
   - title: Building Effective Unit Tests
     path: /training/testing/unit-testing/index.html
-    custom_link_attributes:
-    - description="How to build effective unit tests for Android apps."
+    path_attributes:
+    - name: description
+      value: How to build effective unit tests for Android apps.
     section:
     - title: Building Local Unit Tests
       path: /training/testing/unit-testing/local-unit-tests.html
@@ -1158,8 +1425,9 @@
       path: /training/testing/unit-testing/instrumented-unit-tests.html
   - title: Automating UI Tests
     path: /training/testing/ui-testing/index.html
-    custom_link_attributes:
-    - description="How to automate your user interface tests for Android apps."
+    path_attributes:
+    - name: description
+      value: How to automate your user interface tests for Android apps.
     section:
     - title: Testing UI for a Single App
       path: /training/testing/ui-testing/espresso-testing.html
@@ -1167,8 +1435,9 @@
       path: /training/testing/ui-testing/uiautomator-testing.html
   - title: Testing App Component Integrations
     path: /training/testing/integration-testing/index.html
-    custom_link_attributes:
-    - description="How to build effective integration tests for Android apps."
+    path_attributes:
+    - name: description
+      value: How to build effective integration tests for Android apps.
     section:
     - title: Testing Your Service
       path: /training/testing/integration-testing/service-testing.html
@@ -1176,16 +1445,18 @@
       path: /training/testing/integration-testing/content-provider-testing.html
   - title: Testing Display Performance
     path: /training/testing/performance.html
-    custom_link_attributes:
-    - description="How to automate UI performance testing."
+    path_attributes:
+    - name: description
+      value: How to automate UI performance testing.
 
 - title: Using Google Play to Distribute & Monetize
   path: /training/distribute.html
   section:
   - title: Selling In-app Products
     path: /training/in-app-billing/index.html
-    custom_link_attributes:
-    - description="How to sell in-app products from your application using In-app Billing."
+    path_attributes:
+    - name: description
+      value: How to sell in-app products from your application using In-app Billing.
     section:
     - title: Preparing Your App
       path: /training/in-app-billing/preparing-iab-app.html
@@ -1197,8 +1468,9 @@
       path: /training/in-app-billing/test-iab-app.html
   - title: Maintaining Multiple APKs
     path: /training/multiple-apks/index.html
-    custom_link_attributes:
-    - description="How to publish your app on Google Play with separate APKs that target different devices, while using a single app listing."
+    path_attributes:
+    - name: description
+      value: How to publish your app on Google Play with separate APKs that target different devices, while using a single app listing.
     section:
     - title: Creating Multiple APKs for Different API Levels
       path: /training/multiple-apks/api.html
diff --git a/docs/image_sources/tools/support-library/appbar-kitkat-orig.png b/docs/image_sources/tools/support-library/appbar-kitkat-orig.png
new file mode 100644
index 0000000..ab680ce
--- /dev/null
+++ b/docs/image_sources/tools/support-library/appbar-kitkat-orig.png
Binary files differ
diff --git a/graphics/java/android/view/PixelCopy.java b/graphics/java/android/view/PixelCopy.java
index 95c930c..29bf963 100644
--- a/graphics/java/android/view/PixelCopy.java
+++ b/graphics/java/android/view/PixelCopy.java
@@ -123,6 +123,9 @@
     public static void request(@NonNull Surface source, @NonNull Bitmap dest,
             @NonNull OnPixelCopyFinishedListener listener, @NonNull Handler listenerThread) {
         validateBitmapDest(dest);
+        if (!source.isValid()) {
+            throw new IllegalArgumentException("Surface isn't valid, source.isValid() == false");
+        }
         // TODO: Make this actually async and fast and cool and stuff
         int result = ThreadedRenderer.copySurfaceInto(source, dest);
         listenerThread.post(new Runnable() {
diff --git a/include/androidfw/ZipUtils.h b/include/androidfw/ZipUtils.h
index 094eaa8..55575d7 100644
--- a/include/androidfw/ZipUtils.h
+++ b/include/androidfw/ZipUtils.h
@@ -21,6 +21,7 @@
 #define __LIBS_ZIPUTILS_H
 
 #include <stdint.h>
+#include <string.h>
 #include <stdio.h>
 #include <time.h>
 
@@ -63,16 +64,21 @@
 
     /*
      * Utility function to convert ZIP's time format to a timespec struct.
+     *
+     * NOTE: this method will clear all existing state from |timespec|.
      */
     static inline void zipTimeToTimespec(uint32_t when, struct tm* timespec) {
         const uint32_t date = when >> 16;
+
+        memset(timespec, 0, sizeof(struct tm));
         timespec->tm_year = ((date >> 9) & 0x7F) + 80; // Zip is years since 1980
-        timespec->tm_mon = (date >> 5) & 0x0F;
+        timespec->tm_mon = ((date >> 5) & 0x0F) - 1;
         timespec->tm_mday = date & 0x1F;
 
         timespec->tm_hour = (when >> 11) & 0x1F;
         timespec->tm_min = (when >> 5) & 0x3F;
         timespec->tm_sec = (when & 0x1F) << 1;
+        timespec->tm_isdst = -1;
     }
 private:
     ZipUtils() {}
diff --git a/libs/androidfw/tests/ZipUtils_test.cpp b/libs/androidfw/tests/ZipUtils_test.cpp
index c6038b5..7293843 100644
--- a/libs/androidfw/tests/ZipUtils_test.cpp
+++ b/libs/androidfw/tests/ZipUtils_test.cpp
@@ -45,7 +45,7 @@
     EXPECT_EQ(2011, t.tm_year + 1900)
             << "Year was improperly converted.";
 
-    EXPECT_EQ(6, t.tm_mon)
+    EXPECT_EQ(5, t.tm_mon)
             << "Month was improperly converted.";
 
     EXPECT_EQ(29, t.tm_mday)
@@ -59,6 +59,11 @@
 
     EXPECT_EQ(40, t.tm_sec)
             << "Second was improperly converted.";
+
+    // We don't have enough information to determine timezone related info.
+    EXPECT_EQ(-1, t.tm_isdst);
+    EXPECT_EQ(0, t.tm_gmtoff);
+    EXPECT_EQ(nullptr, t.tm_zone);
 }
 
 }
diff --git a/libs/hwui/GlopBuilder.cpp b/libs/hwui/GlopBuilder.cpp
index fdbe76a..0a8e3f3 100644
--- a/libs/hwui/GlopBuilder.cpp
+++ b/libs/hwui/GlopBuilder.cpp
@@ -471,18 +471,19 @@
     return *this;
 }
 
-GlopBuilder& GlopBuilder::setFillExternalTexture(Texture& texture) {
+GlopBuilder& GlopBuilder::setFillExternalTexture(Texture& texture, Matrix4& textureTransform) {
     TRIGGER_STAGE(kFillStage);
     REQUIRE_STAGES(kMeshStage | kRoundRectClipStage);
 
     mOutGlop->fill.texture = { &texture,
             GL_TEXTURE_EXTERNAL_OES, GL_LINEAR, GL_CLAMP_TO_EDGE,
-            nullptr };
+            &textureTransform };
 
     setFill(SK_ColorWHITE, 1.0f, SkXfermode::kSrc_Mode, Blend::ModeOrderSwap::NoSwap,
             nullptr, nullptr);
 
     mDescription.modulate = mOutGlop->fill.color.a < 1.0f;
+    mDescription.hasTextureTransform = true;
     return *this;
 }
 
diff --git a/libs/hwui/GlopBuilder.h b/libs/hwui/GlopBuilder.h
index b6c186d..a9dd56f 100644
--- a/libs/hwui/GlopBuilder.h
+++ b/libs/hwui/GlopBuilder.h
@@ -73,7 +73,7 @@
     // TODO: Texture should probably know and own its target.
     // setFillLayer() forces it to GL_TEXTURE which isn't always correct.
     // Similarly setFillLayer normally forces its own wrap & filter mode
-    GlopBuilder& setFillExternalTexture(Texture& texture);
+    GlopBuilder& setFillExternalTexture(Texture& texture, Matrix4& textureTransform);
 
     GlopBuilder& setTransform(const Snapshot& snapshot, const int transformFlags) {
         return setTransform(*snapshot.transform, transformFlags);
diff --git a/libs/hwui/Matrix.h b/libs/hwui/Matrix.h
index 36007cd..9cde5d6 100644
--- a/libs/hwui/Matrix.h
+++ b/libs/hwui/Matrix.h
@@ -236,6 +236,8 @@
 
     static const Matrix4& identity();
 
+    void invalidateType() { mType = kTypeUnknown; }
+
 private:
     mutable uint8_t mType;
 
diff --git a/libs/hwui/Readback.cpp b/libs/hwui/Readback.cpp
index 49596e1..55f823d 100644
--- a/libs/hwui/Readback.cpp
+++ b/libs/hwui/Readback.cpp
@@ -101,7 +101,10 @@
     // Setup the source
     sp<GraphicBuffer> sourceBuffer;
     sp<Fence> sourceFence;
-    status_t err = surface.getLastQueuedBuffer(&sourceBuffer, &sourceFence);
+    Matrix4 texTransform;
+    status_t err = surface.getLastQueuedBuffer(&sourceBuffer, &sourceFence,
+            texTransform.data);
+    texTransform.invalidateType();
     if (err != NO_ERROR) {
         ALOGW("Failed to get last queued buffer, error = %d", err);
         return CopyResult::UnknownError;
@@ -163,8 +166,8 @@
         Glop glop;
         GlopBuilder(renderState, caches, &glop)
                 .setRoundRectClipState(nullptr)
-                .setMeshTexturedUvQuad(nullptr, Rect(0, 1, 1, 0)) // TODO: simplify with VBO
-                .setFillExternalTexture(sourceTexture)
+                .setMeshTexturedUnitQuad(nullptr)
+                .setFillExternalTexture(sourceTexture, texTransform)
                 .setTransform(Matrix4::identity(), TransformFlags::None)
                 .setModelViewMapUnitToRect(destRect)
                 .build();
diff --git a/media/java/android/media/MediaCodecInfo.java b/media/java/android/media/MediaCodecInfo.java
index 05e12a1..a8c2652 100644
--- a/media/java/android/media/MediaCodecInfo.java
+++ b/media/java/android/media/MediaCodecInfo.java
@@ -2688,20 +2688,20 @@
         public static final int VP9Profile3HDR = 0x2000;
 
         // from OMX_VIDEO_VP9LEVELTYPE
-        public static final int VP9Level1  = 0x0;
-        public static final int VP9Level11 = 0x1;
-        public static final int VP9Level2  = 0x2;
-        public static final int VP9Level21 = 0x4;
-        public static final int VP9Level3  = 0x8;
-        public static final int VP9Level31 = 0x10;
-        public static final int VP9Level4  = 0x20;
-        public static final int VP9Level41 = 0x40;
-        public static final int VP9Level5  = 0x80;
-        public static final int VP9Level51 = 0x100;
-        public static final int VP9Level52 = 0x200;
-        public static final int VP9Level6  = 0x400;
-        public static final int VP9Level61 = 0x800;
-        public static final int VP9Level62 = 0x1000;
+        public static final int VP9Level1  = 0x1;
+        public static final int VP9Level11 = 0x2;
+        public static final int VP9Level2  = 0x4;
+        public static final int VP9Level21 = 0x8;
+        public static final int VP9Level3  = 0x10;
+        public static final int VP9Level31 = 0x20;
+        public static final int VP9Level4  = 0x40;
+        public static final int VP9Level41 = 0x80;
+        public static final int VP9Level5  = 0x100;
+        public static final int VP9Level51 = 0x200;
+        public static final int VP9Level52 = 0x400;
+        public static final int VP9Level6  = 0x800;
+        public static final int VP9Level61 = 0x1000;
+        public static final int VP9Level62 = 0x2000;
 
         // from OMX_VIDEO_HEVCPROFILETYPE
         public static final int HEVCProfileMain        = 0x01;
diff --git a/media/java/android/media/tv/TvInputManager.java b/media/java/android/media/tv/TvInputManager.java
index 1d894e1..22bb5f1 100644
--- a/media/java/android/media/tv/TvInputManager.java
+++ b/media/java/android/media/tv/TvInputManager.java
@@ -188,6 +188,9 @@
             RECORDING_ERROR_RESOURCE_BUSY})
     public @interface RecordingError {}
 
+    static final int RECORDING_ERROR_START = 0;
+    static final int RECORDING_ERROR_END = 2;
+
     /**
      * Error for {@link TvInputService.RecordingSession#notifyError(int)} and
      * {@link TvRecordingClient.RecordingCallback#onError(int)}: The requested operation cannot be
@@ -195,7 +198,7 @@
      * for the problem is defined on the higher version than application's
      * <code>android:targetSdkVersion</code>.
      */
-    public static final int RECORDING_ERROR_UNKNOWN = 0;
+    public static final int RECORDING_ERROR_UNKNOWN = RECORDING_ERROR_START;
 
     /**
      * Error for {@link TvInputService.RecordingSession#notifyError(int)} and
@@ -209,7 +212,7 @@
      * {@link TvRecordingClient.RecordingCallback#onError(int)}: Recording cannot proceed because
      * a required recording resource was not able to be allocated.
      */
-    public static final int RECORDING_ERROR_RESOURCE_BUSY = 2;
+    public static final int RECORDING_ERROR_RESOURCE_BUSY = RECORDING_ERROR_END;
 
     /** @hide */
     @Retention(RetentionPolicy.SOURCE)
diff --git a/media/java/android/media/tv/TvInputService.java b/media/java/android/media/tv/TvInputService.java
index 488b284..168fcdc 100644
--- a/media/java/android/media/tv/TvInputService.java
+++ b/media/java/android/media/tv/TvInputService.java
@@ -1613,7 +1613,14 @@
          * <li>{@link TvInputManager#RECORDING_ERROR_RESOURCE_BUSY}
          * </ul>
          */
-        public void notifyError(@TvInputManager.RecordingError final int error) {
+        public void notifyError(@TvInputManager.RecordingError int error) {
+            if (error < TvInputManager.RECORDING_ERROR_START
+                    || error > TvInputManager.RECORDING_ERROR_END) {
+                Log.w(TAG, "notifyError - invalid error code (" + error
+                        + ") is changed to RECORDING_ERROR_UNKNOWN.");
+                error = TvInputManager.RECORDING_ERROR_UNKNOWN;
+            }
+            final int validError = error;
             executeOrPostRunnableOnMainThread(new Runnable() {
                 @MainThread
                 @Override
@@ -1621,7 +1628,7 @@
                     try {
                         if (DEBUG) Log.d(TAG, "notifyError");
                         if (mSessionCallback != null) {
-                            mSessionCallback.onError(error);
+                            mSessionCallback.onError(validError);
                         }
                     } catch (RemoteException e) {
                         Log.w(TAG, "error in notifyError", e);
diff --git a/packages/SettingsLib/res/values/strings.xml b/packages/SettingsLib/res/values/strings.xml
index 74c98e4..efa34ff 100644
--- a/packages/SettingsLib/res/values/strings.xml
+++ b/packages/SettingsLib/res/values/strings.xml
@@ -421,8 +421,6 @@
     <string name="wifi_aggressive_handover">Aggressive Wi\u2011Fi to Cellular handover</string>
     <!-- Setting Checkbox title whether to enable WiFi Scanning in the presence of traffic. [CHAR LIMIT=80] -->
     <string name="wifi_allow_scan_with_traffic">Always allow Wi\u2011Fi Roam Scans</string>
-    <!-- Setting Checkbox title whether to enable WiFi Scanning in the presence of traffic. [CHAR LIMIT=80] -->
-    <string name="legacy_dhcp_client">Use legacy DHCP client</string>
     <!-- Setting Checkbox title whether to always keep cellular data active. [CHAR LIMIT=80] -->
     <string name="mobile_data_always_on">Cellular data always active</string>
     <!-- Setting Checkbox title for disabling Bluetooth absolute volume -->
diff --git a/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java b/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
index c72f5d2..0962d84 100644
--- a/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
+++ b/packages/SystemUI/src/com/android/systemui/ImageWallpaper.java
@@ -158,6 +158,7 @@
         private int mLastRequestedHeight = -1;
         private AsyncTask<Void, Void, Bitmap> mLoader;
         private boolean mNeedsDrawAfterLoadingWallpaper;
+        private boolean mSurfaceValid;
 
         public DrawableEngine() {
             super();
@@ -249,11 +250,6 @@
         }
 
         @Override
-        public void onTouchEvent(MotionEvent event) {
-            super.onTouchEvent(event);
-        }
-
-        @Override
         public void onOffsetsChanged(float xOffset, float yOffset,
                 float xOffsetStep, float yOffsetStep,
                 int xPixels, int yPixels) {
@@ -288,13 +284,23 @@
         @Override
         public void onSurfaceDestroyed(SurfaceHolder holder) {
             super.onSurfaceDestroyed(holder);
+            if (DEBUG) {
+                Log.i(TAG, "onSurfaceDestroyed");
+            }
+
             mLastSurfaceWidth = mLastSurfaceHeight = -1;
+            mSurfaceValid = false;
         }
 
         @Override
         public void onSurfaceCreated(SurfaceHolder holder) {
             super.onSurfaceCreated(holder);
+            if (DEBUG) {
+                Log.i(TAG, "onSurfaceCreated");
+            }
+
             mLastSurfaceWidth = mLastSurfaceHeight = -1;
+            mSurfaceValid = true;
         }
 
         @Override
@@ -314,6 +320,9 @@
         }
 
         void drawFrame() {
+            if (!mSurfaceValid) {
+                return;
+            }
             try {
                 DisplayInfo displayInfo = getDefaultDisplayInfo();
                 int newRotation = displayInfo.rotation;
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 23e3561..f7ecd61 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/PhoneStatusBar.java
@@ -1985,19 +1985,29 @@
                 artworkDrawable = new BitmapDrawable(mBackdropBack.getResources(), artworkBitmap);
             }
         }
+        boolean allowWhenShade = false;
         if (ENABLE_LOCKSCREEN_WALLPAPER && artworkDrawable == null) {
             Bitmap lockWallpaper = mLockscreenWallpaper.getBitmap();
             if (lockWallpaper != null) {
                 artworkDrawable = new LockscreenWallpaper.WallpaperDrawable(
                         mBackdropBack.getResources(), lockWallpaper);
+                // We're in the SHADE mode on the SIM screen - yet we still need to show
+                // the lockscreen wallpaper in that mode.
+                allowWhenShade = mStatusBarKeyguardViewManager != null
+                        && mStatusBarKeyguardViewManager.isShowing();
             }
         }
 
+        boolean hideBecauseOccluded = mStatusBarKeyguardViewManager != null
+                && mStatusBarKeyguardViewManager.isOccluded();
+
         final boolean hasArtwork = artworkDrawable != null;
 
-        if ((hasArtwork || DEBUG_MEDIA_FAKE_ARTWORK) && mState != StatusBarState.SHADE
+        if ((hasArtwork || DEBUG_MEDIA_FAKE_ARTWORK)
+                && (mState != StatusBarState.SHADE || allowWhenShade)
                 && mFingerprintUnlockController.getMode()
-                        != FingerprintUnlockController.MODE_WAKE_AND_UNLOCK_PULSING) {
+                        != FingerprintUnlockController.MODE_WAKE_AND_UNLOCK_PULSING
+                && !hideBecauseOccluded) {
             // time to show some art!
             if (mBackdrop.getVisibility() != View.VISIBLE) {
                 mBackdrop.setVisibility(View.VISIBLE);
@@ -2065,7 +2075,8 @@
                     Log.v(TAG, "DEBUG_MEDIA: Fading out album artwork");
                 }
                 if (mFingerprintUnlockController.getMode()
-                        == FingerprintUnlockController.MODE_WAKE_AND_UNLOCK_PULSING) {
+                        == FingerprintUnlockController.MODE_WAKE_AND_UNLOCK_PULSING
+                        || hideBecauseOccluded) {
 
                     // We are unlocking directly - no animation!
                     mBackdrop.setVisibility(View.GONE);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java
index 117e2b3..dcad75a 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java
@@ -247,6 +247,7 @@
             }
         }
         mOccluded = occluded;
+        mPhoneStatusBar.updateMediaMetaData(false, false);
         mStatusBarWindowManager.setKeyguardOccluded(occluded);
         reset();
     }
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 c82ba3b..6800772 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/UserSwitcherController.java
@@ -119,7 +119,7 @@
         filter.addAction(Intent.ACTION_USER_REMOVED);
         filter.addAction(Intent.ACTION_USER_INFO_CHANGED);
         filter.addAction(Intent.ACTION_USER_SWITCHED);
-        filter.addAction(Intent.ACTION_USER_STOPPING);
+        filter.addAction(Intent.ACTION_USER_STOPPED);
         filter.addAction(Intent.ACTION_USER_UNLOCKED);
         mContext.registerReceiverAsUser(mReceiver, UserHandle.SYSTEM, filter,
                 null /* permission */, null /* scheduler */);
diff --git a/packages/SystemUI/src/com/android/systemui/tv/pip/PipRecentsOverlayManager.java b/packages/SystemUI/src/com/android/systemui/tv/pip/PipRecentsOverlayManager.java
index dd12360..fe5d8bce 100644
--- a/packages/SystemUI/src/com/android/systemui/tv/pip/PipRecentsOverlayManager.java
+++ b/packages/SystemUI/src/com/android/systemui/tv/pip/PipRecentsOverlayManager.java
@@ -134,7 +134,8 @@
      */
     public void requestFocus(boolean allowRecentsFocusable) {
         mRecentsView.setVisibility(allowRecentsFocusable ? View.VISIBLE : View.GONE);
-        if (!mIsPipRecentsOverlayShown || !mIsRecentsShown || mIsPipFocusedInRecent) {
+        if (!mIsPipRecentsOverlayShown || !mIsRecentsShown || mIsPipFocusedInRecent
+                || !mPipManager.isPipShown()) {
             return;
         }
         mIsPipFocusedInRecent = true;
@@ -153,7 +154,8 @@
      * This should be called only by {@link com.android.systemui.recents.tv.RecentsTvActivity}.
      */
     public void clearFocus() {
-        if (!mIsPipRecentsOverlayShown || !mIsRecentsShown || !mIsPipFocusedInRecent) {
+        if (!mIsPipRecentsOverlayShown || !mIsRecentsShown || !mIsPipFocusedInRecent
+                || !mPipManager.isPipShown()) {
             return;
         }
         if (!mRecentsView.hasFocus()) {
diff --git a/proto/src/metrics_constants.proto b/proto/src/metrics_constants.proto
index f49235c..c417fe8 100644
--- a/proto/src/metrics_constants.proto
+++ b/proto/src/metrics_constants.proto
@@ -2187,6 +2187,10 @@
     // reinflation.
     ACTION_REMOTE_INPUT_CLOSE = 400;
 
+    // OPEN: Settings > Accounts > Work profile settings
+    // CATEGORY: SETTINGS
+    ACCOUNTS_WORK_PROFILE_SETTINGS = 401;
+
     // Add new aosp constants above this line.
     // END OF AOSP CONSTANTS
   }
diff --git a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
index fc2e95d..ae31438 100644
--- a/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
+++ b/services/accessibility/java/com/android/server/accessibility/AccessibilityManagerService.java
@@ -1245,8 +1245,8 @@
     private void updateServicesLocked(UserState userState) {
         Map<ComponentName, Service> componentNameToServiceMap =
                 userState.mComponentNameToServiceMap;
-        boolean isUnlocked = mContext.getSystemService(UserManager.class)
-                .isUserUnlocked(userState.mUserId);
+        boolean isUnlockingOrUnlocked = mContext.getSystemService(UserManager.class)
+                .isUserUnlockingOrUnlocked(userState.mUserId);
 
         for (int i = 0, count = userState.mInstalledServices.size(); i < count; i++) {
             AccessibilityServiceInfo installedService = userState.mInstalledServices.get(i);
@@ -1256,7 +1256,7 @@
             Service service = componentNameToServiceMap.get(componentName);
 
             // Ignore non-encryption-aware services until user is unlocked
-            if (!isUnlocked && !installedService.isDirectBootAware()) {
+            if (!isUnlockingOrUnlocked && !installedService.isDirectBootAware()) {
                 Slog.d(LOG_TAG, "Ignoring non-encryption-aware service " + componentName);
                 continue;
             }
diff --git a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
index 0428ecf..7b9d4456 100644
--- a/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
+++ b/services/appwidget/java/com/android/server/appwidget/AppWidgetServiceImpl.java
@@ -335,7 +335,7 @@
                     Provider provider = installedProviders.get(i);
 
                     final int userId = provider.getUserId();
-                    if (!mUserManager.isUserUnlocked(userId) ||
+                    if (!mUserManager.isUserUnlockingOrUnlocked(userId) ||
                             isProfileWithLockedParent(userId)) {
                         continue;
                     }
@@ -369,7 +369,7 @@
     }
 
     private void onPackageBroadcastReceived(Intent intent, int userId) {
-        if (!mUserManager.isUserUnlocked(userId) ||
+        if (!mUserManager.isUserUnlockingOrUnlocked(userId) ||
                 isProfileWithLockedParent(userId)) {
             return;
         }
@@ -455,7 +455,7 @@
      * userId must be the group parent.
      */
     private void reloadWidgetsMaskedStateForGroup(int userId) {
-        if (!mUserManager.isUserUnlocked(userId)) {
+        if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
             return;
         }
         synchronized (mLock) {
@@ -472,7 +472,7 @@
         try {
             UserInfo user  = mUserManager.getUserInfo(userId);
 
-            boolean lockedProfile = !mUserManager.isUserUnlocked(userId);
+            boolean lockedProfile = !mUserManager.isUserUnlockingOrUnlocked(userId);
             boolean quietProfile = user.isQuietModeEnabled();
             final int N = mProviders.size();
             for (int i = 0; i < N; i++) {
@@ -656,7 +656,7 @@
     }
 
     private void ensureGroupStateLoadedLocked(int userId) {
-        if (!mUserManager.isUserUnlocked(userId)) {
+        if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
             throw new IllegalStateException(
                     "User " + userId + " must be unlocked for widgets to be available");
         }
@@ -3363,7 +3363,7 @@
             if (userInfo != null && userInfo.isManagedProfile()) {
                 UserInfo parentInfo = mUserManager.getProfileParent(userId);
                 if (parentInfo != null
-                        && !mUserManager.isUserUnlocked(parentInfo.getUserHandle())) {
+                        && !mUserManager.isUserUnlockingOrUnlocked(parentInfo.getUserHandle())) {
                     return true;
                 }
             }
@@ -3378,7 +3378,7 @@
         if (userInfo != null && userInfo.isManagedProfile()) {
             UserInfo parentInfo = mUserManager.getProfileParent(userId);
             if (parentInfo != null
-                    && mUserManager.isUserUnlocked(parentInfo.getUserHandle())) {
+                    && mUserManager.isUserUnlockingOrUnlocked(parentInfo.getUserHandle())) {
                 return true;
             }
         }
diff --git a/services/core/java/com/android/server/ConnectivityService.java b/services/core/java/com/android/server/ConnectivityService.java
index 0287332..d85827e 100644
--- a/services/core/java/com/android/server/ConnectivityService.java
+++ b/services/core/java/com/android/server/ConnectivityService.java
@@ -730,7 +730,7 @@
         //set up the listener for user state for creating user VPNs
         IntentFilter intentFilter = new IntentFilter();
         intentFilter.addAction(Intent.ACTION_USER_STARTING);
-        intentFilter.addAction(Intent.ACTION_USER_STOPPING);
+        intentFilter.addAction(Intent.ACTION_USER_STOPPED);
         intentFilter.addAction(Intent.ACTION_USER_ADDED);
         intentFilter.addAction(Intent.ACTION_USER_REMOVED);
         intentFilter.addAction(Intent.ACTION_USER_UNLOCKED);
@@ -3619,7 +3619,7 @@
         synchronized(mVpns) {
             Vpn userVpn = mVpns.get(userId);
             if (userVpn == null) {
-                loge("Stopping user has no VPN");
+                loge("Stopped user has no VPN");
                 return;
             }
             mVpns.delete(userId);
@@ -3664,7 +3664,7 @@
 
             if (Intent.ACTION_USER_STARTING.equals(action)) {
                 onUserStart(userId);
-            } else if (Intent.ACTION_USER_STOPPING.equals(action)) {
+            } else if (Intent.ACTION_USER_STOPPED.equals(action)) {
                 onUserStop(userId);
             } else if (Intent.ACTION_USER_ADDED.equals(action)) {
                 onUserAdded(userId);
diff --git a/services/core/java/com/android/server/InputMethodManagerService.java b/services/core/java/com/android/server/InputMethodManagerService.java
index 79d16da..a584f70 100644
--- a/services/core/java/com/android/server/InputMethodManagerService.java
+++ b/services/core/java/com/android/server/InputMethodManagerService.java
@@ -1020,7 +1020,7 @@
         // If the system is not ready or the device is not yed unlocked by the user, then we use
         // copy-on-write settings.
         final boolean useCopyOnWriteSettings =
-                !mSystemReady || !mUserManager.isUserUnlocked(newUserId);
+                !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(newUserId);
         mSettings.switchCurrentUser(newUserId, useCopyOnWriteSettings);
         updateCurrentProfileIds();
         // InputMethodFileManager should be reset when the user is changed
@@ -1077,7 +1077,7 @@
                 mSystemReady = true;
                 final int currentUserId = mSettings.getCurrentUserId();
                 mSettings.switchCurrentUser(currentUserId,
-                        !mUserManager.isUserUnlocked(currentUserId));
+                        !mUserManager.isUserUnlockingOrUnlocked(currentUserId));
                 mKeyguardManager = mContext.getSystemService(KeyguardManager.class);
                 mNotificationManager = mContext.getSystemService(NotificationManager.class);
                 mStatusBar = statusBar;
diff --git a/services/core/java/com/android/server/LockSettingsService.java b/services/core/java/com/android/server/LockSettingsService.java
index a3ef6b6b..cbf7e80 100644
--- a/services/core/java/com/android/server/LockSettingsService.java
+++ b/services/core/java/com/android/server/LockSettingsService.java
@@ -256,13 +256,13 @@
         for (int i = 0; i < users.size(); i++) {
             UserInfo user = users.get(i);
             UserHandle userHandle = user.getUserHandle();
-            if (!mUserManager.isUserUnlocked(userHandle)) {
+            if (!mUserManager.isUserUnlockingOrUnlocked(userHandle)) {
                 if (!user.isManagedProfile()) {
                     showEncryptionNotification(userHandle);
                 } else {
                     UserInfo parent = mUserManager.getProfileParent(user.id);
                     if (parent != null &&
-                            mUserManager.isUserUnlocked(parent.getUserHandle()) &&
+                            mUserManager.isUserUnlockingOrUnlocked(parent.getUserHandle()) &&
                             !mUserManager.isQuietModeEnabled(userHandle)) {
                         // Only show notifications for managed profiles once their parent
                         // user is unlocked.
@@ -350,7 +350,7 @@
             UserInfo profile = profiles.get(i);
             if (profile.isManagedProfile()) {
                 UserHandle userHandle = profile.getUserHandle();
-                if (!mUserManager.isUserUnlocked(userHandle) &&
+                if (!mUserManager.isUserUnlockingOrUnlocked(userHandle) &&
                         !mUserManager.isQuietModeEnabled(userHandle)) {
                     showEncryptionNotificationForProfile(userHandle);
                 }
@@ -1281,8 +1281,14 @@
         // service can't connect to vold, it restarts, and then the new instance
         // does successfully connect.
         final IMountService service = getMountService();
-        String password = service.getPassword();
-        service.clearPassword();
+        String password;
+        long identity = Binder.clearCallingIdentity();
+        try {
+            password = service.getPassword();
+            service.clearPassword();
+        } finally {
+            Binder.restoreCallingIdentity(identity);
+        }
         if (password == null) {
             return false;
         }
diff --git a/services/core/java/com/android/server/MountService.java b/services/core/java/com/android/server/MountService.java
index ec05dae..7253870 100644
--- a/services/core/java/com/android/server/MountService.java
+++ b/services/core/java/com/android/server/MountService.java
@@ -2648,6 +2648,8 @@
      */
     @Override
     public int getPasswordType() {
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
+            "no permission to access the crypt keeper");
 
         waitForReady();
 
@@ -2672,6 +2674,8 @@
      */
     @Override
     public void setField(String field, String contents) throws RemoteException {
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
+            "no permission to access the crypt keeper");
 
         waitForReady();
 
@@ -2690,6 +2694,8 @@
      */
     @Override
     public String getField(String field) throws RemoteException {
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
+            "no permission to access the crypt keeper");
 
         waitForReady();
 
@@ -2714,6 +2720,8 @@
      */
     @Override
     public boolean isConvertibleToFBE() throws RemoteException {
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
+            "no permission to access the crypt keeper");
 
         waitForReady();
 
@@ -2728,8 +2736,9 @@
 
     @Override
     public String getPassword() throws RemoteException {
-        mContext.enforceCallingOrSelfPermission(Manifest.permission.ACCESS_KEYGUARD_SECURE_STORAGE,
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
                 "only keyguard can retrieve password");
+
         if (!isReady()) {
             return new String();
         }
@@ -2752,6 +2761,9 @@
 
     @Override
     public void clearPassword() throws RemoteException {
+        mContext.enforceCallingOrSelfPermission(Manifest.permission.STORAGE_INTERNAL,
+                "only keyguard can clear password");
+
         if (!isReady()) {
             return;
         }
@@ -2816,17 +2828,19 @@
         enforcePermission(android.Manifest.permission.STORAGE_INTERNAL);
         waitForReady();
 
-        // When a user has secure lock screen, require a challenge token to
-        // actually unlock. This check is mostly in place for emulation mode.
-        if (mLockPatternUtils.isSecure(userId) && ArrayUtils.isEmpty(token)) {
-            throw new IllegalStateException("Token required to unlock secure user " + userId);
-        }
+        if (StorageManager.isFileEncryptedNativeOrEmulated()) {
+            // When a user has secure lock screen, require a challenge token to
+            // actually unlock. This check is mostly in place for emulation mode.
+            if (mLockPatternUtils.isSecure(userId) && ArrayUtils.isEmpty(token)) {
+                throw new IllegalStateException("Token required to unlock secure user " + userId);
+            }
 
-        try {
-            mCryptConnector.execute("cryptfs", "unlock_user_key", userId, serialNumber,
-                    encodeBytes(token), encodeBytes(secret));
-        } catch (NativeDaemonConnectorException e) {
-            throw e.rethrowAsParcelableException();
+            try {
+                mCryptConnector.execute("cryptfs", "unlock_user_key", userId, serialNumber,
+                        encodeBytes(token), encodeBytes(secret));
+            } catch (NativeDaemonConnectorException e) {
+                throw e.rethrowAsParcelableException();
+            }
         }
 
         synchronized (mLock) {
@@ -2852,12 +2866,8 @@
 
     @Override
     public boolean isUserKeyUnlocked(int userId) {
-        if (StorageManager.isFileEncryptedNativeOrEmulated()) {
-            synchronized (mLock) {
-                return ArrayUtils.contains(mLocalUnlockedUsers, userId);
-            }
-        } else {
-            return true;
+        synchronized (mLock) {
+            return ArrayUtils.contains(mLocalUnlockedUsers, userId);
         }
     }
 
diff --git a/services/core/java/com/android/server/TextServicesManagerService.java b/services/core/java/com/android/server/TextServicesManagerService.java
index a628747..4b0d4be 100644
--- a/services/core/java/com/android/server/TextServicesManagerService.java
+++ b/services/core/java/com/android/server/TextServicesManagerService.java
@@ -166,7 +166,7 @@
         mMonitor = new TextServicesMonitor();
         mMonitor.register(context, null, true);
         final boolean useCopyOnWriteSettings =
-                !mSystemReady || !mUserManager.isUserUnlocked(userId);
+                !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(userId);
         mSettings = new TextServicesSettings(context.getContentResolver(), userId,
                 useCopyOnWriteSettings);
 
@@ -176,7 +176,7 @@
 
     private void resetInternalState(@UserIdInt int userId) {
         final boolean useCopyOnWriteSettings =
-                !mSystemReady || !mUserManager.isUserUnlocked(userId);
+                !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(userId);
         mSettings.switchCurrentUser(userId, useCopyOnWriteSettings);
         updateCurrentProfileIds();
         unbindServiceLocked();
diff --git a/services/core/java/com/android/server/accounts/AccountManagerService.java b/services/core/java/com/android/server/accounts/AccountManagerService.java
index 480da72..96214d6 100644
--- a/services/core/java/com/android/server/accounts/AccountManagerService.java
+++ b/services/core/java/com/android/server/accounts/AccountManagerService.java
@@ -304,7 +304,7 @@
     }
 
     private final SparseArray<UserAccounts> mUsers = new SparseArray<>();
-    private final SparseBooleanArray mUnlockedUsers = new SparseBooleanArray();
+    private final SparseBooleanArray mLocalUnlockedUsers = new SparseBooleanArray();
 
     private static AtomicReference<AccountManagerService> sThis = new AtomicReference<>();
     private static final Account[] EMPTY_ACCOUNT_ARRAY = new Account[]{};
@@ -424,7 +424,7 @@
         if (Log.isLoggable(TAG, Log.DEBUG)) {
             Log.d(TAG, "validateAccountsInternal " + accounts.userId
                     + " isCeDatabaseAttached=" + accounts.openHelper.isCeDatabaseAttached()
-                    + " userLocked=" + mUnlockedUsers.get(accounts.userId));
+                    + " userLocked=" + mLocalUnlockedUsers.get(accounts.userId));
         }
         if (invalidateAuthenticatorCache) {
             mAuthenticatorCache.invalidateCache(accounts.userId);
@@ -575,7 +575,7 @@
                 validateAccounts = true;
             }
             // open CE database if necessary
-            if (!accounts.openHelper.isCeDatabaseAttached() && mUnlockedUsers.get(userId)) {
+            if (!accounts.openHelper.isCeDatabaseAttached() && mLocalUnlockedUsers.get(userId)) {
                 Log.i(TAG, "User " + userId + " is unlocked - opening CE database");
                 synchronized (accounts.cacheLock) {
                     File preNDatabaseFile = new File(getPreNDatabaseName(userId));
@@ -648,8 +648,8 @@
         synchronized (mUsers) {
             accounts = mUsers.get(userId);
             mUsers.remove(userId);
-            userUnlocked = mUnlockedUsers.get(userId);
-            mUnlockedUsers.delete(userId);
+            userUnlocked = mLocalUnlockedUsers.get(userId);
+            mLocalUnlockedUsers.delete(userId);
         }
         if (accounts != null) {
             synchronized (accounts.cacheLock) {
@@ -686,7 +686,7 @@
             Log.v(TAG, "onUserUnlocked " + userId);
         }
         synchronized (mUsers) {
-            mUnlockedUsers.put(userId, true);
+            mLocalUnlockedUsers.put(userId, true);
         }
         if (userId < 1) return;
         syncSharedAccounts(userId);
@@ -746,7 +746,7 @@
         if (account == null) {
             return null;
         }
-        if (!isUserUnlocked(accounts.userId)) {
+        if (!isLocalUnlockedUser(accounts.userId)) {
             Log.w(TAG, "Password is not available - user " + accounts.userId + " data is locked");
             return null;
         }
@@ -828,7 +828,7 @@
                     account.type);
             throw new SecurityException(msg);
         }
-        if (!isUserUnlocked(userId)) {
+        if (!isLocalUnlockedUser(userId)) {
             Log.w(TAG, "User " + userId + " data is locked. callingUid " + callingUid);
             return null;
         }
@@ -1109,7 +1109,7 @@
         if (account == null) {
             return false;
         }
-        if (!isUserUnlocked(accounts.userId)) {
+        if (!isLocalUnlockedUser(accounts.userId)) {
             Log.w(TAG, "Account " + account + " cannot be added - user " + accounts.userId
                     + " is locked. callingUid=" + callingUid);
             return false;
@@ -1176,9 +1176,9 @@
         return true;
     }
 
-    private boolean isUserUnlocked(int userId) {
+    private boolean isLocalUnlockedUser(int userId) {
         synchronized (mUsers) {
-            return mUnlockedUsers.get(userId);
+            return mLocalUnlockedUsers.get(userId);
         }
     }
 
@@ -1193,7 +1193,7 @@
         for (UserInfo user : users) {
             if (user.isRestricted() && (parentUserId == user.restrictedProfileParentId)) {
                 addSharedAccountAsUser(account, user.id);
-                if (getUserManager().isUserUnlocked(user.id)) {
+                if (isLocalUnlockedUser(user.id)) {
                     mMessageHandler.sendMessage(mMessageHandler.obtainMessage(
                             MESSAGE_COPY_SHARED_ACCOUNT, parentUserId, user.id, account));
                 }
@@ -1597,7 +1597,7 @@
 
     private boolean removeAccountInternal(UserAccounts accounts, Account account, int callingUid) {
         int deleted;
-        boolean userUnlocked = isUserUnlocked(accounts.userId);
+        boolean userUnlocked = isLocalUnlockedUser(accounts.userId);
         if (!userUnlocked) {
             Slog.i(TAG, "Removing account " + account + " while user "+ accounts.userId
                     + " is still locked. CE data will be removed later");
@@ -1792,7 +1792,7 @@
                     account.type);
             throw new SecurityException(msg);
         }
-        if (!isUserUnlocked(userId)) {
+        if (!isLocalUnlockedUser(userId)) {
             Log.w(TAG, "Authtoken not available - user " + userId + " data is locked. callingUid "
                     + callingUid);
             return null;
@@ -4037,8 +4037,7 @@
                 return false;
             }
 
-            final ActivityManager am = mContext.getSystemService(ActivityManager.class);
-            if (am.isUserRunningAndLocked(mAccounts.userId)
+            if (!isLocalUnlockedUser(mAccounts.userId)
                     && !authenticatorInfo.componentInfo.directBootAware) {
                 Slog.w(TAG, "Blocking binding to authenticator " + authenticatorInfo.componentName
                         + " which isn't encryption aware");
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 9d7ddc7..ddb9b8a 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -1946,9 +1946,7 @@
                     startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_UNAWARE);
                 }
                 installEncryptionUnawareProviders(userId);
-                if (msg.obj instanceof ProgressReporter) {
-                    ((ProgressReporter) msg.obj).finish();
-                }
+                mUserController.finishUserUnlocked((UserState) msg.obj);
                 break;
             }
             case SYSTEM_USER_CURRENT_MSG: {
@@ -5949,6 +5947,15 @@
 
     }
 
+    final boolean clearBroadcastQueueForUserLocked(int userId) {
+        boolean didSomething = false;
+        for (int i = mBroadcastQueues.length - 1; i >= 0; i--) {
+            didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked(
+                    null, null, userId, true);
+        }
+        return didSomething;
+    }
+
     final boolean forceStopPackageLocked(String packageName, int appId,
             boolean callerWillRestart, boolean purgeCache, boolean doit,
             boolean evenPersistent, boolean uninstalling, int userId, String reason) {
@@ -6304,7 +6311,11 @@
         app.debugging = false;
         app.cached = false;
         app.killedByAm = false;
-        app.unlocked = mContext.getSystemService(UserManager.class).isUserUnlocked(app.userId);
+
+        // We carefully use the same state that PackageManager uses for
+        // filtering, since we use this flag to decide if we need to install
+        // providers when user is unlocked later
+        app.unlocked = StorageManager.isUserKeyUnlocked(app.userId);
 
         mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
 
@@ -11024,14 +11035,6 @@
      * belonging to any running apps.
      */
     private void installEncryptionUnawareProviders(int userId) {
-        if (!StorageManager.isFileEncryptedNativeOrEmulated()) {
-            // TODO: eventually pivot this back to look at current user state,
-            // similar to the comment in UserManager.isUserUnlocked(), but for
-            // now, if we started apps when "unlocked" then unaware providers
-            // have already been spun up.
-            return;
-        }
-
         // We're only interested in providers that are encryption unaware, and
         // we don't care about uninstalled apps, since there's no way they're
         // running at this point.
@@ -17178,6 +17181,7 @@
             if (isProtectedBroadcast
                     || Intent.ACTION_CLOSE_SYSTEM_DIALOGS.equals(action)
                     || Intent.ACTION_DISMISS_KEYBOARD_SHORTCUTS.equals(action)
+                    || Intent.ACTION_MEDIA_BUTTON.equals(action)
                     || Intent.ACTION_MEDIA_SCANNER_SCAN_FILE.equals(action)
                     || Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(action)
                     || AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action)
diff --git a/services/core/java/com/android/server/am/ActivityStarter.java b/services/core/java/com/android/server/am/ActivityStarter.java
index 94e442f..33b87b6 100644
--- a/services/core/java/com/android/server/am/ActivityStarter.java
+++ b/services/core/java/com/android/server/am/ActivityStarter.java
@@ -685,8 +685,8 @@
                     Binder.restoreCallingIdentity(token);
                 }
                 if (parent != null
-                        && userManager.isUserUnlocked(parent.getUserHandle())
-                        && !userManager.isUserUnlocked(userInfo.getUserHandle())) {
+                        && userManager.isUserUnlockingOrUnlocked(parent.getUserHandle())
+                        && !userManager.isUserUnlockingOrUnlocked(userInfo.getUserHandle())) {
                     rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId,
                             PackageManager.MATCH_DIRECT_BOOT_AWARE
                                     | PackageManager.MATCH_DIRECT_BOOT_UNAWARE);
diff --git a/services/core/java/com/android/server/am/UserController.java b/services/core/java/com/android/server/am/UserController.java
index cdb68d8..bfa5b42 100644
--- a/services/core/java/com/android/server/am/UserController.java
+++ b/services/core/java/com/android/server/am/UserController.java
@@ -270,7 +270,7 @@
             if (mStartedUsers.get(uss.mHandle.getIdentifier()) != uss) return;
 
             // Only keep marching forward if user is actually unlocked
-            if (!isUserKeyUnlocked(userId)) return;
+            if (!StorageManager.isUserKeyUnlocked(userId)) return;
 
             if (uss.setState(STATE_RUNNING_LOCKED, STATE_RUNNING_UNLOCKING)) {
                 uss.mUnlockProgress.start();
@@ -281,9 +281,29 @@
                 mUserManager.onBeforeUnlockUser(userId);
                 uss.mUnlockProgress.setProgress(20);
 
-                // Dispatch unlocked to system services
-                mHandler.obtainMessage(SYSTEM_USER_UNLOCK_MSG, userId, 0, uss.mUnlockProgress)
+                // Dispatch unlocked to system services; when fully dispatched,
+                // that calls through to the next "unlocked" phase
+                mHandler.obtainMessage(SYSTEM_USER_UNLOCK_MSG, userId, 0, uss)
                         .sendToTarget();
+            }
+        }
+    }
+
+    /**
+     * Step from {@link UserState#STATE_RUNNING_UNLOCKING} to
+     * {@link UserState#STATE_RUNNING_UNLOCKED}.
+     */
+    void finishUserUnlocked(final UserState uss) {
+        final int userId = uss.mHandle.getIdentifier();
+        synchronized (mService) {
+            // Bail if we ended up with a stale user
+            if (mStartedUsers.get(uss.mHandle.getIdentifier()) != uss) return;
+
+            // Only keep marching forward if user is actually unlocked
+            if (!StorageManager.isUserKeyUnlocked(userId)) return;
+
+            if (uss.setState(STATE_RUNNING_UNLOCKING, STATE_RUNNING_UNLOCKED)) {
+                uss.mUnlockProgress.finish();
 
                 // Dispatch unlocked to external apps
                 final Intent unlockedIntent = new Intent(Intent.ACTION_USER_UNLOCKED);
@@ -310,27 +330,25 @@
                     }
                 }
 
-                // Send PRE_BOOT broadcasts if fingerprint changed
+                // Send PRE_BOOT broadcasts if user fingerprint changed; we
+                // purposefully block sending BOOT_COMPLETED until after all
+                // PRE_BOOT receivers are finished to avoid ANR'ing apps
                 final UserInfo info = getUserInfo(userId);
                 if (!Objects.equals(info.lastLoggedInFingerprint, Build.FINGERPRINT)) {
                     new PreBootBroadcaster(mService, userId, null) {
                         @Override
                         public void onFinished() {
-                            finishUserUnlocked(uss);
+                            finishUserUnlockedCompleted(uss);
                         }
                     }.sendNext();
                 } else {
-                    finishUserUnlocked(uss);
+                    finishUserUnlockedCompleted(uss);
                 }
             }
         }
     }
 
-    /**
-     * Step from {@link UserState#STATE_RUNNING_UNLOCKING} to
-     * {@link UserState#STATE_RUNNING_UNLOCKED}.
-     */
-    private void finishUserUnlocked(UserState uss) {
+    private void finishUserUnlockedCompleted(UserState uss) {
         final int userId = uss.mHandle.getIdentifier();
         synchronized (mService) {
             // Bail if we ended up with a stale user
@@ -341,39 +359,38 @@
             }
 
             // Only keep marching forward if user is actually unlocked
-            if (!isUserKeyUnlocked(userId)) return;
+            if (!StorageManager.isUserKeyUnlocked(userId)) return;
 
-            if (uss.setState(STATE_RUNNING_UNLOCKING, STATE_RUNNING_UNLOCKED)) {
-                // Remember that we logged in
-                mUserManager.onUserLoggedIn(userId);
+            // Remember that we logged in
+            mUserManager.onUserLoggedIn(userId);
 
-                if (!userInfo.isInitialized()) {
-                    if (userId != UserHandle.USER_SYSTEM) {
-                        Slog.d(TAG, "Initializing user #" + userId);
-                        Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE);
-                        intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
-                        mService.broadcastIntentLocked(null, null, intent, null,
-                                new IIntentReceiver.Stub() {
-                                    @Override
-                                    public void performReceive(Intent intent, int resultCode,
-                                            String data, Bundle extras, boolean ordered,
-                                            boolean sticky, int sendingUser) {
-                                        // Note: performReceive is called with mService lock held
-                                        getUserManager().makeInitialized(userInfo.id);
-                                    }
-                                }, 0, null, null, null, AppOpsManager.OP_NONE,
-                                null, true, false, MY_PID, SYSTEM_UID, userId);
-                    }
+            if (!userInfo.isInitialized()) {
+                if (userId != UserHandle.USER_SYSTEM) {
+                    Slog.d(TAG, "Initializing user #" + userId);
+                    Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE);
+                    intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+                    mService.broadcastIntentLocked(null, null, intent, null,
+                            new IIntentReceiver.Stub() {
+                                @Override
+                                public void performReceive(Intent intent, int resultCode,
+                                        String data, Bundle extras, boolean ordered,
+                                        boolean sticky, int sendingUser) {
+                                    // Note: performReceive is called with mService lock held
+                                    getUserManager().makeInitialized(userInfo.id);
+                                }
+                            }, 0, null, null, null, AppOpsManager.OP_NONE,
+                            null, true, false, MY_PID, SYSTEM_UID, userId);
                 }
-                Slog.d(TAG, "Sending BOOT_COMPLETE user #" + userId);
-                final Intent bootIntent = new Intent(Intent.ACTION_BOOT_COMPLETED, null);
-                bootIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
-                bootIntent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT
-                        | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND);
-                mService.broadcastIntentLocked(null, null, bootIntent, null, null, 0, null, null,
-                        new String[] { android.Manifest.permission.RECEIVE_BOOT_COMPLETED },
-                        AppOpsManager.OP_NONE, null, true, false, MY_PID, SYSTEM_UID, userId);
             }
+
+            Slog.d(TAG, "Sending BOOT_COMPLETE user #" + userId);
+            final Intent bootIntent = new Intent(Intent.ACTION_BOOT_COMPLETED, null);
+            bootIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
+            bootIntent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT
+                    | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND);
+            mService.broadcastIntentLocked(null, null, bootIntent, null, null, 0, null, null,
+                    new String[] { android.Manifest.permission.RECEIVE_BOOT_COMPLETED },
+                    AppOpsManager.OP_NONE, null, true, false, MY_PID, SYSTEM_UID, userId);
         }
     }
 
@@ -483,6 +500,8 @@
                         });
                     }
                 };
+                // Clear broadcast queue for the user to avoid delivering stale broadcasts
+                mService.clearBroadcastQueueForUserLocked(userId);
                 // Kick things off.
                 mService.broadcastIntentLocked(null, null, stoppingIntent,
                         null, stoppingReceiver, 0, null, null,
@@ -680,20 +699,6 @@
         return IMountService.Stub.asInterface(ServiceManager.getService("mount"));
     }
 
-    private boolean isUserKeyUnlocked(int userId) {
-        final IMountService mountService = getMountService();
-        if (mountService != null) {
-            try {
-                return mountService.isUserKeyUnlocked(userId);
-            } catch (RemoteException e) {
-                throw e.rethrowAsRuntimeException();
-            }
-        } else {
-            Slog.w(TAG, "Mount service not published; guessing locked state based on property");
-            return !StorageManager.isFileEncryptedNativeOrEmulated();
-        }
-    }
-
     /**
      * Start user, if its not already running.
      * <p>The user will be brought to the foreground, if {@code foreground} parameter is set.
@@ -935,7 +940,7 @@
             }
         }
 
-        if (!isUserKeyUnlocked(userId)) {
+        if (!StorageManager.isUserKeyUnlocked(userId)) {
             final UserInfo userInfo = getUserInfo(userId);
             final IMountService mountService = getMountService();
             try {
@@ -1321,30 +1326,31 @@
         if ((flags & ActivityManager.FLAG_OR_STOPPED) != 0) {
             return true;
         }
-
-        final boolean unlocked;
-        switch (state.state) {
-            case UserState.STATE_STOPPING:
-            case UserState.STATE_SHUTDOWN:
-            default:
-                return false;
-
-            case UserState.STATE_BOOTING:
-            case UserState.STATE_RUNNING_LOCKED:
-                unlocked = false;
-                break;
-
-            case UserState.STATE_RUNNING_UNLOCKING:
-            case UserState.STATE_RUNNING_UNLOCKED:
-                unlocked = true;
-                break;
-        }
-
         if ((flags & ActivityManager.FLAG_AND_LOCKED) != 0) {
-            return !unlocked;
+            switch (state.state) {
+                case UserState.STATE_BOOTING:
+                case UserState.STATE_RUNNING_LOCKED:
+                    return true;
+                default:
+                    return false;
+            }
+        }
+        if ((flags & ActivityManager.FLAG_AND_UNLOCKING_OR_UNLOCKED) != 0) {
+            switch (state.state) {
+                case UserState.STATE_RUNNING_UNLOCKING:
+                case UserState.STATE_RUNNING_UNLOCKED:
+                    return true;
+                default:
+                    return false;
+            }
         }
         if ((flags & ActivityManager.FLAG_AND_UNLOCKED) != 0) {
-            return unlocked;
+            switch (state.state) {
+                case UserState.STATE_RUNNING_UNLOCKED:
+                    return true;
+                default:
+                    return false;
+            }
         }
 
         // One way or another, we're running!
diff --git a/services/core/java/com/android/server/content/SyncManager.java b/services/core/java/com/android/server/content/SyncManager.java
index fcf2162..493fc4a 100644
--- a/services/core/java/com/android/server/content/SyncManager.java
+++ b/services/core/java/com/android/server/content/SyncManager.java
@@ -396,8 +396,8 @@
                 onUserRemoved(userId);
             } else if (Intent.ACTION_USER_UNLOCKED.equals(action)) {
                 onUserUnlocked(userId);
-            } else if (Intent.ACTION_USER_STOPPING.equals(action)) {
-                onUserStopping(userId);
+            } else if (Intent.ACTION_USER_STOPPED.equals(action)) {
+                onUserStopped(userId);
             }
         }
     };
@@ -550,7 +550,7 @@
         intentFilter = new IntentFilter();
         intentFilter.addAction(Intent.ACTION_USER_REMOVED);
         intentFilter.addAction(Intent.ACTION_USER_UNLOCKED);
-        intentFilter.addAction(Intent.ACTION_USER_STOPPING);
+        intentFilter.addAction(Intent.ACTION_USER_STOPPED);
         mContext.registerReceiverAsUser(
                 mUserIntentReceiver, UserHandle.ALL, intentFilter, null, null);
 
@@ -1422,7 +1422,7 @@
         }
     }
 
-    private void onUserStopping(int userId) {
+    private void onUserStopped(int userId) {
         updateRunningAccounts(null /* Don't sync any target */);
 
         cancelActiveSync(
diff --git a/services/core/java/com/android/server/fingerprint/EnrollClient.java b/services/core/java/com/android/server/fingerprint/EnrollClient.java
index b636ce5..6a533c9 100644
--- a/services/core/java/com/android/server/fingerprint/EnrollClient.java
+++ b/services/core/java/com/android/server/fingerprint/EnrollClient.java
@@ -51,7 +51,8 @@
                     " getGroupId():" + getGroupId());
         }
         if (remaining == 0) {
-            FingerprintUtils.getInstance().addFingerprintForUser(getContext(), fingerId, groupId);
+            FingerprintUtils.getInstance().addFingerprintForUser(getContext(), fingerId,
+                    getTargetUserId());
         }
         return sendEnrollResult(fingerId, groupId, remaining);
     }
diff --git a/services/core/java/com/android/server/fingerprint/FingerprintService.java b/services/core/java/com/android/server/fingerprint/FingerprintService.java
index 9a2db8e..ae01635 100644
--- a/services/core/java/com/android/server/fingerprint/FingerprintService.java
+++ b/services/core/java/com/android/server/fingerprint/FingerprintService.java
@@ -540,13 +540,15 @@
         startClient(client, true /* initiatedByClient */);
     }
 
-    private void startEnrollment(IBinder token, byte [] cryptoToken, int callingUserId, int groupId,
+    private void startEnrollment(IBinder token, byte [] cryptoToken, int userId,
             IFingerprintServiceReceiver receiver, int flags, boolean restricted,
             String opPackageName) {
-        updateActiveGroup(groupId, opPackageName);
+        updateActiveGroup(userId, opPackageName);
+
+        final int groupId = userId; // default group for fingerprint enrollment
 
         EnrollClient client = new EnrollClient(getContext(), mHalDeviceId, token, receiver,
-                callingUserId, groupId, cryptoToken, restricted, opPackageName) {
+                userId, groupId, cryptoToken, restricted, opPackageName) {
 
             @Override
             public IFingerprintDaemon getFingerprintDaemon() {
@@ -680,15 +682,14 @@
         }
 
         @Override // Binder call
-        public void enroll(final IBinder token, final byte[] cryptoToken, final int groupId,
+        public void enroll(final IBinder token, final byte[] cryptoToken, final int userId,
                 final IFingerprintServiceReceiver receiver, final int flags,
                 final String opPackageName) {
             checkPermission(MANAGE_FINGERPRINT);
             final int limit =  mContext.getResources().getInteger(
                     com.android.internal.R.integer.config_fingerprintMaxTemplatesPerUser);
-            final int callingUserId = UserHandle.getCallingUserId();
-            final int enrolled = FingerprintService.this.
-                    getEnrolledFingerprints(callingUserId).size();
+
+            final int enrolled = FingerprintService.this.getEnrolledFingerprints(userId).size();
             if (enrolled >= limit) {
                 Slog.w(TAG, "Too many fingerprints registered");
                 return;
@@ -696,7 +697,7 @@
 
             // Group ID is arbitrarily set to parent profile user ID. It just represents
             // the default fingerprints for the user.
-            if (!isCurrentUserOrProfile(groupId)) {
+            if (!isCurrentUserOrProfile(userId)) {
                 return;
             }
 
@@ -704,7 +705,7 @@
             mHandler.post(new Runnable() {
                 @Override
                 public void run() {
-                    startEnrollment(token, cryptoToken, callingUserId, groupId, receiver, flags,
+                    startEnrollment(token, cryptoToken, userId, receiver, flags,
                             restricted, opPackageName);
                 }
             });
diff --git a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
index 0b1ece5..30aab8c 100644
--- a/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
+++ b/services/core/java/com/android/server/net/NetworkPolicyManagerService.java
@@ -465,7 +465,7 @@
                 continue;
             }
             for (int j = 0; j < numberUsers; j++) {
-                final UserInfo user = users.get(i);
+                final UserInfo user = users.get(j);
                 final int uid = UserHandle.getUid(user.id, app.uid);
                 mDefaultRestrictBackgroundWhitelistUids.append(uid, true);
                 if (LOGD) Slog.d(TAG, "revoked whistelist status for uid " + uid + ": "
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index 89dc4fb..ba651fc 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -2674,14 +2674,8 @@
             // Prepare storage for system user really early during boot,
             // since core system apps like SettingsProvider and SystemUI
             // can't wait for user to start
-            final int storageFlags;
-            if (StorageManager.isFileEncryptedNativeOrEmulated()) {
-                storageFlags = StorageManager.FLAG_STORAGE_DE;
-            } else {
-                storageFlags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
-            }
             reconcileAppsDataLI(StorageManager.UUID_PRIVATE_INTERNAL, UserHandle.USER_SYSTEM,
-                    storageFlags);
+                    StorageManager.FLAG_STORAGE_DE);
 
             // If this is first boot after an OTA, and a normal boot, then
             // we need to clear code cache directories.
@@ -3112,7 +3106,7 @@
 
     @Override
     public void checkPackageStartable(String packageName, int userId) {
-        final boolean userKeyUnlocked = isUserKeyUnlocked(userId);
+        final boolean userKeyUnlocked = StorageManager.isUserKeyUnlocked(userId);
 
         synchronized (mPackages) {
             final PackageSetting ps = mSettings.mPackages.get(packageName);
@@ -3463,30 +3457,6 @@
     }
 
     /**
-     * Return if the user key is currently unlocked.
-     */
-    private boolean isUserKeyUnlocked(int userId) {
-        if (StorageManager.isFileEncryptedNativeOrEmulated()) {
-            final IMountService mount = IMountService.Stub
-                    .asInterface(ServiceManager.getService("mount"));
-            if (mount == null) {
-                Slog.w(TAG, "Early during boot, assuming locked");
-                return false;
-            }
-            final long token = Binder.clearCallingIdentity();
-            try {
-                return mount.isUserKeyUnlocked(userId);
-            } catch (RemoteException e) {
-                throw e.rethrowAsRuntimeException();
-            } finally {
-                Binder.restoreCallingIdentity(token);
-            }
-        } else {
-            return true;
-        }
-    }
-
-    /**
      * Update given flags based on encryption status of current user.
      */
     private int updateFlags(int flags, int userId) {
@@ -3497,7 +3467,7 @@
             // give them what they want
         } else {
             // Caller expressed no opinion, so match based on user state
-            if (isUserKeyUnlocked(userId)) {
+            if (StorageManager.isUserKeyUnlocked(userId)) {
                 flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE;
             } else {
                 flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE;
@@ -16106,7 +16076,7 @@
 
         final UserManager um = mContext.getSystemService(UserManager.class);
         final int flags;
-        if (um.isUserUnlocked(userId)) {
+        if (um.isUserUnlockingOrUnlocked(userId)) {
             flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
         } else if (um.isUserRunning(userId)) {
             flags = StorageManager.FLAG_STORAGE_DE;
@@ -18790,7 +18760,7 @@
         final UserManager um = mContext.getSystemService(UserManager.class);
         for (UserInfo user : um.getUsers()) {
             final int flags;
-            if (um.isUserUnlocked(user.id)) {
+            if (um.isUserUnlockingOrUnlocked(user.id)) {
                 flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
             } else if (um.isUserRunning(user.id)) {
                 flags = StorageManager.FLAG_STORAGE_DE;
@@ -19104,7 +19074,7 @@
         // First look for stale data that doesn't belong, and check if things
         // have changed since we did our last restorecon
         if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) {
-            if (!isUserKeyUnlocked(userId)) {
+            if (!StorageManager.isUserKeyUnlocked(userId)) {
                 throw new RuntimeException(
                         "Yikes, someone asked us to reconcile CE storage while " + userId
                                 + " was still locked; this would have caused massive data loss!");
@@ -19212,7 +19182,7 @@
         final UserManager um = mContext.getSystemService(UserManager.class);
         for (UserInfo user : um.getUsers()) {
             final int flags;
-            if (um.isUserUnlocked(user.id)) {
+            if (um.isUserUnlockingOrUnlocked(user.id)) {
                 flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
             } else if (um.isUserRunning(user.id)) {
                 flags = StorageManager.FLAG_STORAGE_DE;
diff --git a/services/core/java/com/android/server/pm/ShortcutService.java b/services/core/java/com/android/server/pm/ShortcutService.java
index 5764161..c0874ef 100644
--- a/services/core/java/com/android/server/pm/ShortcutService.java
+++ b/services/core/java/com/android/server/pm/ShortcutService.java
@@ -1561,48 +1561,46 @@
 
     // === House keeping ===
 
-    @VisibleForTesting
-    void cleanUpPackageLocked(String packageName, int owningUserId, int packageUserId) {
-        cleanUpPackageLocked(packageName, owningUserId, packageUserId,
-                /* forceForCommandLine= */ false);
+    private void cleanUpPackageForAllLoadedUsers(String packageName, @UserIdInt int packageUserId) {
+        synchronized (mLock) {
+            forEachLoadedUserLocked(user ->
+                    cleanUpPackageLocked(packageName, user.getUserId(), packageUserId));
+        }
     }
 
     /**
      * 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).
+     *
+     * This is called when an app is uninstalled, or an app gets "clear data"ed.
      */
-    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;
-        }
-
+    @VisibleForTesting
+    void cleanUpPackageLocked(String packageName, int owningUserId, int packageUserId) {
         final boolean wasUserLoaded = isUserLoadedLocked(owningUserId);
 
-        final ShortcutUser mUser = getUserShortcutsLocked(owningUserId);
+        final ShortcutUser user = getUserShortcutsLocked(owningUserId);
         boolean doNotify = false;
 
         // First, remove the package from the package list (if the package is a publisher).
         if (packageUserId == owningUserId) {
-            if (mUser.removePackage(this, packageName) != null) {
+            if (user.removePackage(this, packageName) != null) {
                 doNotify = true;
             }
         }
 
         // Also remove from the launcher list (if the package is a launcher).
-        mUser.removeLauncher(packageUserId, packageName);
+        user.removeLauncher(packageUserId, packageName);
 
         // Then remove pinned shortcuts from all launchers.
-        final ArrayMap<PackageWithUser, ShortcutLauncher> launchers = mUser.getAllLaunchers();
+        final ArrayMap<PackageWithUser, ShortcutLauncher> launchers = user.getAllLaunchers();
         for (int i = launchers.size() - 1; i >= 0; i--) {
             launchers.valueAt(i).cleanUpPackage(packageName, packageUserId);
         }
         // Now there may be orphan shortcuts because we removed pinned shortucts at the previous
         // step.  Remove them too.
-        for (int i = mUser.getAllPackages().size() - 1; i >= 0; i--) {
-            mUser.getAllPackages().valueAt(i).refreshPinnedFlags(this);
+        for (int i = user.getAllPackages().size() - 1; i >= 0; i--) {
+            user.getAllPackages().valueAt(i).refreshPinnedFlags(this);
         }
 
         scheduleSaveUser(owningUserId);
@@ -1842,6 +1840,11 @@
         public void onPackageRemoved(String packageName, int uid) {
             handlePackageRemoved(packageName, getChangingUserId());
         }
+
+        @Override
+        public void onPackageDataCleared(String packageName, int uid) {
+            handlePackageDataCleared(packageName, getChangingUserId());
+        }
     };
 
     /**
@@ -1915,16 +1918,15 @@
             Slog.d(TAG, String.format("handlePackageRemoved: %s user=%d", packageName,
                     packageUserId));
         }
-        handlePackageRemovedInner(packageName, packageUserId, /* forceForCommandLine =*/ false);
+        cleanUpPackageForAllLoadedUsers(packageName, packageUserId);
     }
 
-    private void handlePackageRemovedInner(String packageName, @UserIdInt int packageUserId,
-            boolean forceForCommandLine) {
-        synchronized (mLock) {
-            forEachLoadedUserLocked(user ->
-                cleanUpPackageLocked(packageName, user.getUserId(), packageUserId,
-                        forceForCommandLine));
+    private void handlePackageDataCleared(String packageName, int packageUserId) {
+        if (DEBUG) {
+            Slog.d(TAG, String.format("handlePackageDataCleared: %s user=%d", packageName,
+                    packageUserId));
         }
+        cleanUpPackageForAllLoadedUsers(packageName, packageUserId);
     }
 
     // === PackageManager interaction ===
@@ -2390,8 +2392,7 @@
 
             Slog.i(TAG, "cmd: handleClearShortcuts: " + mUserId + ", " + packageName);
 
-            ShortcutService.this.handlePackageRemovedInner(packageName, mUserId,
-                    /* forceForCommandLine= */ true);
+            ShortcutService.this.cleanUpPackageForAllLoadedUsers(packageName, mUserId);
         }
     }
 
diff --git a/services/core/java/com/android/server/pm/UserManagerService.java b/services/core/java/com/android/server/pm/UserManagerService.java
index a085370..a2d859b 100644
--- a/services/core/java/com/android/server/pm/UserManagerService.java
+++ b/services/core/java/com/android/server/pm/UserManagerService.java
@@ -692,7 +692,7 @@
     @Override
     public boolean trySetQuietModeDisabled(int userHandle, IntentSender target) {
         final int credentialOwnerUserId = getCredentialOwnerProfile(userHandle);
-        if (mContext.getSystemService(StorageManager.class).isUserKeyUnlocked(userHandle)
+        if (StorageManager.isUserKeyUnlocked(userHandle)
                 || !mLockPatternUtils.isSecure(credentialOwnerUserId)) {
             // if the user is already unlocked, no need to show a profile challenge
             setQuietModeEnabled(userHandle, false);
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index 827ea5b..2636d09 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -5159,7 +5159,6 @@
             mKeyguardOccluded = false;
             mKeyguardDelegate.setOccluded(false);
             mStatusBar.getAttrs().privateFlags |= PRIVATE_FLAG_KEYGUARD;
-            mStatusBar.getAttrs().flags |= FLAG_SHOW_WALLPAPER;
             return true;
         } else if (!wasOccluded && isOccluded && showing) {
             mKeyguardOccluded = true;
diff --git a/services/core/java/com/android/server/search/SearchManagerService.java b/services/core/java/com/android/server/search/SearchManagerService.java
index e3e1097..4d91814 100644
--- a/services/core/java/com/android/server/search/SearchManagerService.java
+++ b/services/core/java/com/android/server/search/SearchManagerService.java
@@ -112,7 +112,7 @@
             if (um.getUserInfo(userId) == null) {
                 throw new IllegalStateException("User " + userId + " doesn't exist");
             }
-            if (!um.isUserUnlocked(userId)) {
+            if (!um.isUserUnlockingOrUnlocked(userId)) {
                 throw new IllegalStateException("User " + userId + " isn't unlocked");
             }
         } finally {
diff --git a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
index d6ace91..af7e66d 100644
--- a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
+++ b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
@@ -862,7 +862,6 @@
 
         IntentFilter userFilter = new IntentFilter();
         userFilter.addAction(Intent.ACTION_USER_REMOVED);
-        userFilter.addAction(Intent.ACTION_USER_STOPPING);
         mContext.registerReceiver(new BroadcastReceiver() {
             @Override
             public void onReceive(Context context, Intent intent) {
@@ -871,12 +870,6 @@
                     onRemoveUser(intent.getIntExtra(Intent.EXTRA_USER_HANDLE,
                             UserHandle.USER_NULL));
                 }
-                // TODO: Race condition causing problems when cleaning up on stopping a user.
-                // Comment this out for now.
-                // else if (Intent.ACTION_USER_STOPPING.equals(action)) {
-                //     onStoppingUser(intent.getIntExtra(Intent.EXTRA_USER_HANDLE,
-                //             UserHandle.USER_NULL));
-                // }
             }
         }, userFilter);
 
diff --git a/services/core/java/com/android/server/wm/AppWindowToken.java b/services/core/java/com/android/server/wm/AppWindowToken.java
index 3b1f34a..b4ead44 100644
--- a/services/core/java/com/android/server/wm/AppWindowToken.java
+++ b/services/core/java/com/android/server/wm/AppWindowToken.java
@@ -390,8 +390,8 @@
     }
 
     boolean hasSavedSurface() {
-        for (int i = windows.size() -1; i >= 0; i--) {
-            final WindowState ws = windows.get(i);
+        for (int i = allAppWindows.size() -1; i >= 0; i--) {
+            final WindowState ws = allAppWindows.get(i);
             if (ws.hasSavedSurface()) {
                 return true;
             }
@@ -408,8 +408,8 @@
         // Check if we have enough drawn windows to mark allDrawn= true.
         int numInteresting = 0;
         int numDrawn = 0;
-        for (int i = windows.size() - 1; i >= 0; i--) {
-            WindowState w = windows.get(i);
+        for (int i = allAppWindows.size() - 1; i >= 0; i--) {
+            WindowState w = allAppWindows.get(i);
             if (w.hasSavedSurface()) {
                 w.restoreSavedSurface();
             }
@@ -429,8 +429,8 @@
     }
 
     void destroySavedSurfaces() {
-        for (int i = windows.size() - 1; i >= 0; i--) {
-            WindowState win = windows.get(i);
+        for (int i = allAppWindows.size() - 1; i >= 0; i--) {
+            WindowState win = allAppWindows.get(i);
             win.destroySavedSurface();
         }
         mAnimatingWithSavedSurface = false;
diff --git a/services/core/java/com/android/server/wm/BoundsAnimationController.java b/services/core/java/com/android/server/wm/BoundsAnimationController.java
index debb382..220a6de 100644
--- a/services/core/java/com/android/server/wm/BoundsAnimationController.java
+++ b/services/core/java/com/android/server/wm/BoundsAnimationController.java
@@ -24,10 +24,12 @@
 import android.animation.Animator;
 import android.animation.ValueAnimator;
 import android.graphics.Rect;
+import android.os.IBinder;
 import android.os.Debug;
 import android.util.ArrayMap;
 import android.util.Slog;
 import android.view.animation.LinearInterpolator;
+import android.view.WindowManagerInternal;
 
 /**
  * Enables animating bounds of objects.
@@ -49,6 +51,32 @@
     // Only accessed on UI thread.
     private ArrayMap<AnimateBoundsUser, BoundsAnimator> mRunningAnimations = new ArrayMap<>();
 
+    private final WindowManagerInternal.AppTransitionListener mAppTransitionNotifier
+        = new WindowManagerInternal.AppTransitionListener() {
+                public void onAppTransitionCancelledLocked() {
+                    animationFinished();
+                }
+                public void onAppTransitionFinishedLocked(IBinder token) {
+                    animationFinished();
+                }
+                private void animationFinished() {
+                    if (mFinishAnimationAfterTransition) {
+                        for (int i = 0; i < mRunningAnimations.size(); i++) {
+                            BoundsAnimator b = mRunningAnimations.valueAt(i);
+                            b.onAnimationEnd(null);
+                        }
+                    }
+                }
+            };
+
+    private final AppTransition mAppTransition;
+    private boolean mFinishAnimationAfterTransition = false;
+
+    BoundsAnimationController(AppTransition transition) {
+        mAppTransition = transition;
+        mAppTransition.registerListenerLocked(mAppTransitionNotifier);
+    }
+
     private final class BoundsAnimator extends ValueAnimator
             implements ValueAnimator.AnimatorUpdateListener, ValueAnimator.AnimatorListener {
         private final AnimateBoundsUser mTarget;
@@ -129,6 +157,7 @@
         public void onAnimationStart(Animator animation) {
             if (DEBUG) Slog.d(TAG, "onAnimationStart: mTarget=" + mTarget
                     + " mReplacement=" + mReplacement);
+            mFinishAnimationAfterTransition = false;
             // Ensure that we have prepared the target for animation before
             // we trigger any size changes, so it can swap surfaces
             // in to appropriate modes, or do as it wishes otherwise.
@@ -150,10 +179,21 @@
             if (DEBUG) Slog.d(TAG, "onAnimationEnd: mTarget=" + mTarget
                     + " mMoveToFullScreen=" + mMoveToFullScreen + " mWillReplace=" + mWillReplace);
 
-            finishAnimation();
+            // There could be another animation running. For example in the
+            // move to fullscreen case, recents will also be closing while the
+            // previous task will be taking its place in the fullscreen stack.
+            // we have to ensure this is completed before we finish the animation
+            // and take our place in the fullscreen stack.
+            if (mAppTransition.isRunning() && !mFinishAnimationAfterTransition) {
+                mFinishAnimationAfterTransition = true;
+                return;
+            }
+
             if (mMoveToFullScreen && !mWillReplace) {
                 mTarget.moveToFullscreen();
             }
+
+            finishAnimation();
         }
 
         @Override
diff --git a/services/core/java/com/android/server/wm/DockedStackDividerController.java b/services/core/java/com/android/server/wm/DockedStackDividerController.java
index 8174c13..c640b2a 100644
--- a/services/core/java/com/android/server/wm/DockedStackDividerController.java
+++ b/services/core/java/com/android/server/wm/DockedStackDividerController.java
@@ -377,7 +377,7 @@
 
         // If the app that having visibility change is not the top visible one in the task,
         // it does not affect whether the docked stack is minimized, ignore it.
-        if (task.getTopVisibleAppToken() == null || task.getTopVisibleAppToken() != wtoken) {
+        if (task.getTopAppToken() == null || task.getTopAppToken() != wtoken) {
             return;
         }
 
@@ -598,7 +598,7 @@
     }
 
     private boolean animateForMinimizedDockedStack(long now) {
-        final TaskStack stack = mDisplayContent.getDockedStackVisibleForUserLocked();
+        final TaskStack stack = mService.mStackIdToStack.get(DOCKED_STACK_ID);
         if (!mAnimationStarted) {
             mAnimationStarted = true;
             mAnimationStartTime = now;
diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java
index 6925fa5..8d41dab 100644
--- a/services/core/java/com/android/server/wm/Task.java
+++ b/services/core/java/com/android/server/wm/Task.java
@@ -719,6 +719,10 @@
         return null;
     }
 
+    AppWindowToken getTopAppToken() {
+        return mAppTokens.size() > 0 ? mAppTokens.get(mAppTokens.size() - 1) : null;
+    }
+
     @Override
     public boolean isFullscreen() {
         if (useCurrentBounds()) {
diff --git a/services/core/java/com/android/server/wm/TaskStack.java b/services/core/java/com/android/server/wm/TaskStack.java
index 7c1d2d7..4224c57 100644
--- a/services/core/java/com/android/server/wm/TaskStack.java
+++ b/services/core/java/com/android/server/wm/TaskStack.java
@@ -1098,6 +1098,14 @@
         pw.println(prefix + "mDeferDetach=" + mDeferDetach);
         pw.println(prefix + "mFullscreen=" + mFullscreen);
         pw.println(prefix + "mBounds=" + mBounds.toShortString());
+        if (mMinimizeAmount != 0f) {
+            pw.println(prefix + "mMinimizeAmout=" + mMinimizeAmount);
+        }
+        if (mAdjustedForIme) {
+            pw.println(prefix + "mAdjustedForIme=true");
+            pw.println(prefix + "mAdjustImeAmount=" + mAdjustImeAmount);
+            pw.println(prefix + "mAdjustDividerAmount=" + mAdjustDividerAmount);
+        }
         if (!mAdjustedBounds.isEmpty()) {
             pw.println(prefix + "mAdjustedBounds=" + mAdjustedBounds.toShortString());
         }
diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java
index 1bd8c32..57f551c 100644
--- a/services/core/java/com/android/server/wm/WindowManagerService.java
+++ b/services/core/java/com/android/server/wm/WindowManagerService.java
@@ -715,8 +715,7 @@
 
     final WindowAnimator mAnimator;
 
-    private final BoundsAnimationController mBoundsAnimationController =
-            new BoundsAnimationController();
+    private final BoundsAnimationController mBoundsAnimationController;
 
     SparseArray<Task> mTaskIdToTask = new SparseArray<>();
 
@@ -974,6 +973,8 @@
         mAppTransition = new AppTransition(context, this);
         mAppTransition.registerListenerLocked(mActivityManagerAppTransitionNotifier);
 
+        mBoundsAnimationController = new BoundsAnimationController(mAppTransition);
+
         mActivityManager = ActivityManagerNative.getDefault();
         mAmInternal = LocalServices.getService(ActivityManagerInternal.class);
         mAppOps = (AppOpsManager)context.getSystemService(Context.APP_OPS_SERVICE);
@@ -4334,15 +4335,21 @@
             }
         }
 
-        if (visibilityChanged && !delayed) {
-            if (visible) {
+        if (visibilityChanged) {
+            if (visible && !delayed) {
                 // The token was made immediately visible, there will be no entrance animation.
                 // We need to inform the client the enter animation was finished.
                 wtoken.mEnteringAnimation = true;
                 mActivityManagerAppTransitionNotifier.onAppTransitionFinishedLocked(wtoken.token);
             }
-            getDefaultDisplayContentLocked().getDockedDividerController()
-                    .notifyAppVisibilityChanged(wtoken, visible);
+
+            if (!mClosingApps.contains(wtoken) && !mOpeningApps.contains(wtoken)) {
+                // The token is not closing nor opening, so even if there is an animation set, that
+                // doesn't mean that it goes through the normal app transition cycle so we have
+                // to inform the docked controller about visibility change.
+                getDefaultDisplayContentLocked().getDockedDividerController()
+                        .notifyAppVisibilityChanged(wtoken, visible);
+            }
         }
 
         return delayed;
diff --git a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
index 56e2001..93fbe5c 100644
--- a/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
+++ b/services/devicepolicy/java/com/android/server/devicepolicy/DevicePolicyManagerService.java
@@ -6224,6 +6224,8 @@
     }
 
     private void enforceUserUnlocked(int userId) {
+        // Since we're doing this operation on behalf of an app, we only
+        // want to use the actual "unlocked" state.
         Preconditions.checkState(mUserManager.isUserUnlocked(userId),
                 "User must be running and unlocked");
     }
diff --git a/services/print/java/com/android/server/print/PrintManagerService.java b/services/print/java/com/android/server/print/PrintManagerService.java
index 4d02928..f2c995b 100644
--- a/services/print/java/com/android/server/print/PrintManagerService.java
+++ b/services/print/java/com/android/server/print/PrintManagerService.java
@@ -727,7 +727,7 @@
 
                 @Override
                 public void onPackageModified(String packageName) {
-                    if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+                    if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
                     UserState userState = getOrCreateUserStateLocked(getChangingUserId(), false);
 
                     synchronized (mLock) {
@@ -742,7 +742,7 @@
 
                 @Override
                 public void onPackageRemoved(String packageName, int uid) {
-                    if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+                    if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
                     UserState userState = getOrCreateUserStateLocked(getChangingUserId(), false);
 
                     synchronized (mLock) {
@@ -757,7 +757,7 @@
                 @Override
                 public boolean onHandleForceStop(Intent intent, String[] stoppedPackages,
                         int uid, boolean doit) {
-                    if (!mUserManager.isUserUnlocked(getChangingUserId())) return false;
+                    if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return false;
                     synchronized (mLock) {
                         // A background user/profile's print jobs are running but there is
                         // no UI shown. Hence, if the packages of such a user change we need
@@ -795,7 +795,7 @@
 
                 @Override
                 public void onPackageAdded(String packageName, int uid) {
-                    if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+                    if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
                     synchronized (mLock) {
                         if (hasPrintService(packageName)) {
                             UserState userState = getOrCreateUserStateLocked(getChangingUserId(),
@@ -812,7 +812,7 @@
         }
 
         private UserState getOrCreateUserStateLocked(int userId, boolean lowPriority) {
-            if (!mUserManager.isUserUnlocked(userId)) {
+            if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
                 throw new IllegalStateException(
                         "User " + userId + " must be unlocked for printing to be available");
             }
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 bc43576..13518b5 100644
--- a/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java
+++ b/services/tests/servicestests/src/com/android/server/pm/ShortcutManagerTest.java
@@ -1061,6 +1061,12 @@
         i.putExtra(Intent.EXTRA_REPLACING, true);
         return i;
     }
+    private Intent genPackageDataClear(String packageName, int userId) {
+        Intent i = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED);
+        i.setData(Uri.parse("package:" + packageName));
+        i.putExtra(Intent.EXTRA_USER_HANDLE, userId);
+        return i;
+    }
 
     private ShortcutInfo parceled(ShortcutInfo si) {
         Parcel p = Parcel.obtain();
@@ -4159,6 +4165,79 @@
         assertFalse(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_10));
     }
 
+    /** Almost ame as testHandlePackageDelete, except it doesn't uninstall packages. */
+    public void testHandlePackageClearData() {
+        final Icon bmp32x32 = Icon.createWithBitmap(BitmapFactory.decodeResource(
+                getTestContext().getResources(), R.drawable.black_32x32));
+        setCaller(CALLING_PACKAGE_1, USER_0);
+        assertTrue(mManager.addDynamicShortcuts(list(
+                makeShortcutWithIcon("s1", bmp32x32), makeShortcutWithIcon("s2", bmp32x32)
+        )));
+
+        setCaller(CALLING_PACKAGE_2, USER_0);
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcutWithIcon("s1", bmp32x32))));
+
+        setCaller(CALLING_PACKAGE_3, USER_0);
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcutWithIcon("s1", bmp32x32))));
+
+        setCaller(CALLING_PACKAGE_1, USER_10);
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcutWithIcon("s1", bmp32x32))));
+
+        setCaller(CALLING_PACKAGE_2, USER_10);
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcutWithIcon("s1", bmp32x32))));
+
+        setCaller(CALLING_PACKAGE_3, USER_10);
+        assertTrue(mManager.addDynamicShortcuts(list(makeShortcutWithIcon("s1", bmp32x32))));
+
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_10));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_10));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_10));
+
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_10));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_10));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_10));
+
+        mService.mPackageMonitor.onReceive(getTestContext(),
+                genPackageDataClear(CALLING_PACKAGE_1, USER_0));
+
+        assertNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_10));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_10));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_10));
+
+        assertFalse(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_10));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_10));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_10));
+
+        mService.mPackageMonitor.onReceive(getTestContext(),
+                genPackageDataClear(CALLING_PACKAGE_2, USER_10));
+
+        assertNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_0));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_1, "s1", USER_10));
+        assertNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_2, "s1", USER_10));
+        assertNotNull(mService.getPackageShortcutForTest(CALLING_PACKAGE_3, "s1", USER_10));
+
+        assertFalse(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_0));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_1, USER_10));
+        assertFalse(bitmapDirectoryExists(CALLING_PACKAGE_2, USER_10));
+        assertTrue(bitmapDirectoryExists(CALLING_PACKAGE_3, USER_10));
+    }
+
     public void testHandlePackageUpdate() throws Throwable {
 
         // Set up shortcuts and launchers.
diff --git a/tests/HwAccelerationTest/AndroidManifest.xml b/tests/HwAccelerationTest/AndroidManifest.xml
index b9e9ac8..3785cdc 100644
--- a/tests/HwAccelerationTest/AndroidManifest.xml
+++ b/tests/HwAccelerationTest/AndroidManifest.xml
@@ -383,6 +383,15 @@
         </activity>
 
         <activity
+                android:name="VideoViewCaptureActivity"
+                android:label="SurfaceView/GetBitmap with Video 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/res/drawable/default_wallpaper.png b/tests/HwAccelerationTest/res/drawable/default_wallpaper.png
index 187a6c0..91ad252 100644
--- a/tests/HwAccelerationTest/res/drawable/default_wallpaper.png
+++ b/tests/HwAccelerationTest/res/drawable/default_wallpaper.png
Binary files differ
diff --git a/tests/HwAccelerationTest/res/raw/colorgrid_video.mp4 b/tests/HwAccelerationTest/res/raw/colorgrid_video.mp4
new file mode 100644
index 0000000..1be8bee
--- /dev/null
+++ b/tests/HwAccelerationTest/res/raw/colorgrid_video.mp4
Binary files differ
diff --git a/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java b/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java
index f658b7c..6fe2cb4 100644
--- a/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java
+++ b/tests/HwAccelerationTest/src/com/android/test/hwui/GetBitmapSurfaceViewActivity.java
@@ -23,6 +23,7 @@
 import android.os.Environment;
 import android.view.Gravity;
 import android.view.PixelCopy;
+import android.view.Surface;
 import android.view.SurfaceHolder;
 import android.view.SurfaceView;
 import android.view.View;
@@ -87,9 +88,42 @@
             android.util.Log.e("TextureView", "Cannot set preview texture target!", t);
         }
 
+        setCameraDisplayOrientation(this, 0, mCamera);
         mCamera.startPreview();
     }
 
+    public static void setCameraDisplayOrientation(Activity activity,
+            int cameraId, android.hardware.Camera camera) {
+        android.hardware.Camera.CameraInfo info = new android.hardware.Camera.CameraInfo();
+        android.hardware.Camera.getCameraInfo(cameraId, info);
+        int rotation = activity.getWindowManager().getDefaultDisplay()
+                .getRotation();
+        int degrees = 0;
+        switch (rotation) {
+            case Surface.ROTATION_0:
+                degrees = 0;
+                break;
+            case Surface.ROTATION_90:
+                degrees = 90;
+                break;
+            case Surface.ROTATION_180:
+                degrees = 180;
+                break;
+            case Surface.ROTATION_270:
+                degrees = 270;
+                break;
+        }
+
+        int result;
+        if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) {
+            result = (info.orientation + degrees) % 360;
+            result = (360 - result) % 360; // compensate the mirror
+        } else { // back-facing
+            result = (info.orientation - degrees + 360) % 360;
+        }
+        camera.setDisplayOrientation(result);
+    }
+
     @Override
     public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
     }
diff --git a/tests/HwAccelerationTest/src/com/android/test/hwui/VideoViewCaptureActivity.java b/tests/HwAccelerationTest/src/com/android/test/hwui/VideoViewCaptureActivity.java
new file mode 100644
index 0000000..b87be80
--- /dev/null
+++ b/tests/HwAccelerationTest/src/com/android/test/hwui/VideoViewCaptureActivity.java
@@ -0,0 +1,89 @@
+/*
+ * 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.net.Uri;
+import android.os.Bundle;
+import android.os.Environment;
+import android.view.PixelCopy;
+import android.view.View;
+import android.widget.Button;
+import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+import android.widget.Toast;
+import android.widget.VideoView;
+
+import java.io.FileOutputStream;
+
+public class VideoViewCaptureActivity extends Activity {
+    private VideoView mVideoView;
+    private int mVideoWidth, mVideoHeight;
+
+    @Override
+    protected void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        mVideoView = new VideoView(this);
+        mVideoView.setOnPreparedListener(mp -> {
+            mp.setLooping(true);
+            mVideoWidth = mp.getVideoWidth();
+            mVideoHeight = mp.getVideoHeight();
+            mVideoView.start();
+        });
+
+        Uri uri = Uri.parse("android.resource://com.android.test.hwui/" + R.raw.colorgrid_video);
+        mVideoView.setVideoURI(uri);
+
+        Button button = new Button(this);
+        button.setText("Copy bitmap to /sdcard/surfaceview.png");
+        button.setOnClickListener((View v) -> {
+            final Bitmap b = Bitmap.createBitmap(
+                    mVideoWidth, mVideoHeight,
+                    Bitmap.Config.ARGB_8888);
+            PixelCopy.request(mVideoView, b,
+                    (int result) -> {
+                        if (result != PixelCopy.SUCCESS) {
+                            Toast.makeText(VideoViewCaptureActivity.this,
+                                    "Failed to copy", Toast.LENGTH_SHORT).show();
+                            return;
+                        }
+                        try {
+                            try (FileOutputStream out = new FileOutputStream(
+                                    Environment.getExternalStorageDirectory() + "/surfaceview.png");) {
+                                b.compress(Bitmap.CompressFormat.PNG, 100, out);
+                            }
+                        } catch (Exception e) {
+                            // Ignore
+                        }
+                    }, mVideoView.getHandler());
+        });
+
+        FrameLayout content = new FrameLayout(this);
+        LinearLayout layout = new LinearLayout(this);
+        layout.setOrientation(LinearLayout.VERTICAL);
+        layout.addView(button, LinearLayout.LayoutParams.MATCH_PARENT,
+                LinearLayout.LayoutParams.WRAP_CONTENT);
+        layout.addView(mVideoView, LinearLayout.LayoutParams.MATCH_PARENT,
+                LinearLayout.LayoutParams.MATCH_PARENT);
+
+        content.addView(layout, new FrameLayout.LayoutParams(
+                FrameLayout.LayoutParams.MATCH_PARENT,
+                FrameLayout.LayoutParams.MATCH_PARENT));
+        setContentView(content);
+    }
+}
diff --git a/tools/aapt/Bundle.h b/tools/aapt/Bundle.h
index ca06ac4..653c1b4 100644
--- a/tools/aapt/Bundle.h
+++ b/tools/aapt/Bundle.h
@@ -55,7 +55,7 @@
           mCompressionMethod(0), mJunkPath(false), mOutputAPKFile(NULL),
           mManifestPackageNameOverride(NULL), mInstrumentationPackageNameOverride(NULL),
           mAutoAddOverlay(false), mGenDependencies(false), mNoVersionVectors(false),
-          mCrunchedOutputDir(NULL), mProguardFile(NULL),
+          mCrunchedOutputDir(NULL), mProguardFile(NULL), mMainDexProguardFile(NULL),
           mAndroidManifestFile(NULL), mPublicOutputFile(NULL),
           mRClassDir(NULL), mResourceIntermediatesDir(NULL), mManifestMinSdkVersion(NULL),
           mMinSdkVersion(NULL), mTargetSdkVersion(NULL), mMaxSdkVersion(NULL),
@@ -146,6 +146,8 @@
     void setCrunchedOutputDir(const char* dir) { mCrunchedOutputDir = dir; }
     const char* getProguardFile() const { return mProguardFile; }
     void setProguardFile(const char* file) { mProguardFile = file; }
+    const char* getMainDexProguardFile() const { return mMainDexProguardFile; }
+    void setMainDexProguardFile(const char* file) { mMainDexProguardFile = file; }
     const android::Vector<const char*>& getResourceSourceDirs() const { return mResourceSourceDirs; }
     void addResourceSourceDir(const char* dir) { mResourceSourceDirs.insertAt(dir,0); }
     const char* getAndroidManifestFile() const { return mAndroidManifestFile; }
@@ -299,6 +301,7 @@
     bool        mNoVersionVectors;
     const char* mCrunchedOutputDir;
     const char* mProguardFile;
+    const char* mMainDexProguardFile;
     const char* mAndroidManifestFile;
     const char* mPublicOutputFile;
     const char* mRClassDir;
diff --git a/tools/aapt/Command.cpp b/tools/aapt/Command.cpp
index db40416..9976d00 100644
--- a/tools/aapt/Command.cpp
+++ b/tools/aapt/Command.cpp
@@ -2631,6 +2631,12 @@
         goto bail;
     }
 
+    // Write out the Main Dex ProGuard file
+    err = writeMainDexProguardFile(bundle, assets);
+    if (err < 0) {
+        goto bail;
+    }
+
     // Write the apk
     if (outputAPKFile) {
         // Gather all resources and add them to the APK Builder. The builder will then
diff --git a/tools/aapt/Main.cpp b/tools/aapt/Main.cpp
index c424cc5..984d98e 100644
--- a/tools/aapt/Main.cpp
+++ b/tools/aapt/Main.cpp
@@ -67,6 +67,7 @@
         "        [--max-res-version VAL] \\\n"
         "        [-I base-package [-I base-package ...]] \\\n"
         "        [-A asset-source-dir]  [-G class-list-file] [-P public-definitions-file] \\\n"
+        "        [-D main-dex-class-list-file] \\\n"
         "        [-S resource-sources [-S resource-sources ...]] \\\n"
         "        [-F apk-file] [-J R-file-dir] \\\n"
         "        [--product product1,product2,...] \\\n"
@@ -120,6 +121,7 @@
         "       localization=\"suggested\"\n"
         "   -A  additional directory in which to find raw asset files\n"
         "   -G  A file to output proguard options into.\n"
+        "   -D  A file to output proguard options for the main dex into.\n"
         "   -F  specify the apk file to output\n"
         "   -I  add an existing package to base include set\n"
         "   -J  specify where to output R.java resource constant definitions\n"
@@ -390,6 +392,17 @@
                 convertPath(argv[0]);
                 bundle.setProguardFile(argv[0]);
                 break;
+            case 'D':
+                argc--;
+                argv++;
+                if (!argc) {
+                    fprintf(stderr, "ERROR: No argument supplied for '-D' option\n");
+                    wantUsage = true;
+                    goto bail;
+                }
+                convertPath(argv[0]);
+                bundle.setMainDexProguardFile(argv[0]);
+                break;
             case 'I':
                 argc--;
                 argv++;
diff --git a/tools/aapt/Main.h b/tools/aapt/Main.h
index e84c4c5..a493842 100644
--- a/tools/aapt/Main.h
+++ b/tools/aapt/Main.h
@@ -54,6 +54,7 @@
         bool includePrivate, bool emitCallback);
 
 extern android::status_t writeProguardFile(Bundle* bundle, const sp<AaptAssets>& assets);
+extern android::status_t writeMainDexProguardFile(Bundle* bundle, const sp<AaptAssets>& assets);
 
 extern bool isValidResourceType(const String8& type);
 
diff --git a/tools/aapt/Resource.cpp b/tools/aapt/Resource.cpp
index 18a1943..8e7045b 100644
--- a/tools/aapt/Resource.cpp
+++ b/tools/aapt/Resource.cpp
@@ -2832,7 +2832,7 @@
 }
 
 status_t
-writeProguardForAndroidManifest(ProguardKeepSet* keep, const sp<AaptAssets>& assets)
+writeProguardForAndroidManifest(ProguardKeepSet* keep, const sp<AaptAssets>& assets, bool mainDex)
 {
     status_t err;
     ResXMLTree tree;
@@ -2844,6 +2844,7 @@
     sp<AaptGroup> assGroup;
     sp<AaptFile> assFile;
     String8 pkg;
+    String8 defaultProcess;
 
     // First, look for a package file to parse.  This is required to
     // be able to generate the resource information.
@@ -2900,6 +2901,15 @@
                     addProguardKeepRule(keep, agent, pkg.string(),
                             assFile->getPrintableSource(), tree.getLineNumber());
                 }
+
+                if (mainDex) {
+                    defaultProcess = AaptXml::getAttribute(tree,
+                            "http://schemas.android.com/apk/res/android", "process", &error);
+                    if (error != "") {
+                        fprintf(stderr, "ERROR: %s\n", error.string());
+                        return -1;
+                    }
+                }
             } else if (tag == "instrumentation") {
                 keepTag = true;
             }
@@ -2916,7 +2926,23 @@
                 fprintf(stderr, "ERROR: %s\n", error.string());
                 return -1;
             }
-            if (name.length() > 0) {
+
+            keepTag = name.length() > 0;
+
+            if (keepTag && mainDex) {
+                String8 componentProcess = AaptXml::getAttribute(tree,
+                        "http://schemas.android.com/apk/res/android", "process", &error);
+                if (error != "") {
+                    fprintf(stderr, "ERROR: %s\n", error.string());
+                    return -1;
+                }
+
+                const String8& process =
+                        componentProcess.length() > 0 ? componentProcess : defaultProcess;
+                keepTag = process.length() > 0 && process.find(":") != 0;
+            }
+
+            if (keepTag) {
                 addProguardKeepRule(keep, name, pkg.string(),
                         assFile->getPrintableSource(), tree.getLineNumber());
             }
@@ -3099,30 +3125,12 @@
 }
 
 status_t
-writeProguardFile(Bundle* bundle, const sp<AaptAssets>& assets)
+writeProguardSpec(const char* filename, const ProguardKeepSet& keep, status_t err)
 {
-    status_t err = -1;
-
-    if (!bundle->getProguardFile()) {
-        return NO_ERROR;
-    }
-
-    ProguardKeepSet keep;
-
-    err = writeProguardForAndroidManifest(&keep, assets);
-    if (err < 0) {
-        return err;
-    }
-
-    err = writeProguardForLayouts(&keep, assets);
-    if (err < 0) {
-        return err;
-    }
-
-    FILE* fp = fopen(bundle->getProguardFile(), "w+");
+    FILE* fp = fopen(filename, "w+");
     if (fp == NULL) {
         fprintf(stderr, "ERROR: Unable to open class file %s: %s\n",
-                bundle->getProguardFile(), strerror(errno));
+                filename, strerror(errno));
         return UNKNOWN_ERROR;
     }
 
@@ -3141,6 +3149,49 @@
     return err;
 }
 
+status_t
+writeProguardFile(Bundle* bundle, const sp<AaptAssets>& assets)
+{
+    status_t err = -1;
+
+    if (!bundle->getProguardFile()) {
+        return NO_ERROR;
+    }
+
+    ProguardKeepSet keep;
+
+    err = writeProguardForAndroidManifest(&keep, assets, false);
+    if (err < 0) {
+        return err;
+    }
+
+    err = writeProguardForLayouts(&keep, assets);
+    if (err < 0) {
+        return err;
+    }
+
+    return writeProguardSpec(bundle->getProguardFile(), keep, err);
+}
+
+status_t
+writeMainDexProguardFile(Bundle* bundle, const sp<AaptAssets>& assets)
+{
+    status_t err = -1;
+
+    if (!bundle->getMainDexProguardFile()) {
+        return NO_ERROR;
+    }
+
+    ProguardKeepSet keep;
+
+    err = writeProguardForAndroidManifest(&keep, assets, true);
+    if (err < 0) {
+        return err;
+    }
+
+    return writeProguardSpec(bundle->getMainDexProguardFile(), keep, err);
+}
+
 // Loops through the string paths and writes them to the file pointer
 // Each file path is written on its own line with a terminating backslash.
 status_t writePathsToFile(const sp<FilePathStore>& files, FILE* fp)
diff --git a/tools/aapt2/link/Link.cpp b/tools/aapt2/link/Link.cpp
index 8c8bffa..4997120 100644
--- a/tools/aapt2/link/Link.cpp
+++ b/tools/aapt2/link/Link.cpp
@@ -1459,6 +1459,21 @@
         return 1;
     }
 
+    // Expand all argument-files passed into the command line. These start with '@'.
+    std::vector<std::string> argList;
+    for (const std::string& arg : flags.getArgs()) {
+        if (util::stringStartsWith<char>(arg, "@")) {
+            const std::string path = arg.substr(1, arg.size() - 1);
+            std::string error;
+            if (!file::appendArgsFromFile(path, &argList, &error)) {
+                context.getDiagnostics()->error(DiagMessage(path) << error);
+                return 1;
+            }
+        } else {
+            argList.push_back(arg);
+        }
+    }
+
     if (verbose) {
         context.setVerbose(verbose);
     }
@@ -1568,7 +1583,7 @@
     }
 
     LinkCommand cmd(&context, options);
-    return cmd.run(flags.getArgs());
+    return cmd.run(argList);
 }
 
 } // namespace aapt
diff --git a/tools/aapt2/util/Files.cpp b/tools/aapt2/util/Files.cpp
index bb093ab..f5e49f1 100644
--- a/tools/aapt2/util/Files.cpp
+++ b/tools/aapt2/util/Files.cpp
@@ -18,6 +18,7 @@
 #include "util/Util.h"
 
 #include <algorithm>
+#include <android-base/file.h>
 #include <cerrno>
 #include <cstdio>
 #include <dirent.h>
@@ -190,6 +191,23 @@
     return std::move(fileMap);
 }
 
+bool appendArgsFromFile(const StringPiece& path, std::vector<std::string>* outArgList,
+                        std::string* outError) {
+    std::string contents;
+    if (!android::base::ReadFileToString(path.toString(), &contents)) {
+        if (outError) *outError = "failed to read argument-list file";
+        return false;
+    }
+
+    for (StringPiece line : util::tokenize<char>(contents, ' ')) {
+        line = util::trimWhitespace(line);
+        if (!line.empty()) {
+            outArgList->push_back(line.toString());
+        }
+    }
+    return true;
+}
+
 bool FileFilter::setPattern(const StringPiece& pattern) {
     mPatternTokens = util::splitAndLowercase(pattern, ':');
     return true;
diff --git a/tools/aapt2/util/Files.h b/tools/aapt2/util/Files.h
index c2e6115..4d8a1fe 100644
--- a/tools/aapt2/util/Files.h
+++ b/tools/aapt2/util/Files.h
@@ -95,6 +95,12 @@
  */
 Maybe<android::FileMap> mmapPath(const StringPiece& path, std::string* outError);
 
+/**
+ * Reads the file at path and appends each line to the outArgList vector.
+ */
+bool appendArgsFromFile(const StringPiece& path, std::vector<std::string>* outArgList,
+                        std::string* outError);
+
 /*
  * Filter that determines which resource files/directories are
  * processed by AAPT. Takes a pattern string supplied by the user.