Merge "Renames ChunkListing.java to ChunkListingMap.java."
diff --git a/core/java/android/view/inputmethod/InputMethodManager.java b/core/java/android/view/inputmethod/InputMethodManager.java
index 8a09788..e63a406 100644
--- a/core/java/android/view/inputmethod/InputMethodManager.java
+++ b/core/java/android/view/inputmethod/InputMethodManager.java
@@ -1373,7 +1373,7 @@
      * @hide
      */
     @Deprecated
-    @UnsupportedAppUsage
+    @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 123768499)
     public void showSoftInputUnchecked(int flags, ResultReceiver resultReceiver) {
         try {
             Log.w(TAG, "showSoftInputUnchecked() is a hidden method, which will be removed "
diff --git a/core/java/com/android/internal/os/ChildZygoteInit.java b/core/java/com/android/internal/os/ChildZygoteInit.java
index cc74863..1f816c1 100644
--- a/core/java/com/android/internal/os/ChildZygoteInit.java
+++ b/core/java/com/android/internal/os/ChildZygoteInit.java
@@ -102,7 +102,7 @@
         // are just isolated UIDs in the range, because for the webview zygote, there is no
         // single range that captures all possible isolated UIDs.
         // TODO(b/123615476) narrow this down
-        if (uidGidMin < Process.FIRST_ISOLATED_UID) {
+        if (uidGidMin < Process.FIRST_APP_ZYGOTE_ISOLATED_UID) {
             throw new RuntimeException("Passed in UID range does not map to isolated processes.");
         }
 
diff --git a/media/java/android/media/session/MediaSessionProviderService.java b/media/java/android/media/session/MediaSessionProviderService.java
deleted file mode 100644
index 9a346ff..0000000
--- a/media/java/android/media/session/MediaSessionProviderService.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.media.session;
-
-import android.app.Service;
-import android.content.Intent;
-import android.os.IBinder;
-
-/**
- * Abstract class for mainline module services.
- *
- * @hide  // TODO: Make it as a @SystemApi
- */
-public abstract class MediaSessionProviderService extends Service {
-
-    @Override
-    public IBinder onBind(Intent intent) {
-        // TODO: Return IMediaSessionProviderService.Stub()
-        return null;
-    }
-}
diff --git a/media/packages/MediaCore/Android.bp.bak b/media/packages/MediaCore/Android.bp.bak
deleted file mode 100644
index c7fd58b..0000000
--- a/media/packages/MediaCore/Android.bp.bak
+++ /dev/null
@@ -1,21 +0,0 @@
-android_app {
-    name: "MediaCore",
-
-    srcs: [
-        "src/**/*.java",
-    ],
-
-    static_libs: [
-        // TODO: Temporarily statically linked. Should go into "libs"
-        "media1",
-    ],
-
-    // System app
-    platform_apis: true,
-
-    // Privileged app
-    privileged: true,
-
-    // Make sure that the implementation only relies on SDK or system APIs.
-    sdk_version: "system_current",
-}
diff --git a/media/packages/MediaCore/AndroidManifest.xml b/media/packages/MediaCore/AndroidManifest.xml
deleted file mode 100644
index 4e2b274..0000000
--- a/media/packages/MediaCore/AndroidManifest.xml
+++ /dev/null
@@ -1,32 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
-/* //device/apps/common/AndroidManifest.xml
-**
-** Copyright 2019, 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.
-*/
--->
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
-    package="com.android.media" coreApp="true" android:sharedUserId="android.uid.system"
-    android:sharedUserLabel="@string/android_system_label">
-    <application android:process="system"
-        android:persistent="true"
-        android:directBootAware="true">
-        <service android:name="AmlMediaSessionProviderService" android:singleUser="true">
-            <intent-filter>
-                <action android:name="android.media.session.MediaSessionProviderService"/>
-            </intent-filter>
-        </service>
-    </application>
-</manifest>
diff --git a/media/packages/MediaCore/res/values/strings.xml b/media/packages/MediaCore/res/values/strings.xml
deleted file mode 100644
index 59fd635..0000000
--- a/media/packages/MediaCore/res/values/strings.xml
+++ /dev/null
@@ -1,21 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2019 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-
-          http://www.apache.org/licenses/LICENSE-2.0
-
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<resources>
-    <!-- Label for the Android system components when they are shown to the user. -->
-    <string name="android_system_label" translatable="false">Android System</string>
-</resources>
-
diff --git a/media/packages/MediaCore/src/com/android/media/AmlMediaSessionProviderService.java b/media/packages/MediaCore/src/com/android/media/AmlMediaSessionProviderService.java
deleted file mode 100644
index 43b95ab..0000000
--- a/media/packages/MediaCore/src/com/android/media/AmlMediaSessionProviderService.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2019 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.media;
-
-import android.content.Context;
-import android.media.session.MediaSessionProviderService;
-import android.os.PowerManager;
-import android.util.Log;
-
-/**
- * System implementation of MediaSessionProviderService
- */
-public class AmlMediaSessionProviderService extends MediaSessionProviderService {
-    private static final String TAG = "AmlMediaSessionProviderS";
-    static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
-
-    private Context mContext;
-
-    public AmlMediaSessionProviderService(Context context) {
-        mContext = context;
-        PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
-    }
-}
diff --git a/services/core/java/com/android/server/inputmethod/InputMethodManagerService.java b/services/core/java/com/android/server/inputmethod/InputMethodManagerService.java
index 144f2b6..96ba084 100644
--- a/services/core/java/com/android/server/inputmethod/InputMethodManagerService.java
+++ b/services/core/java/com/android/server/inputmethod/InputMethodManagerService.java
@@ -667,13 +667,19 @@
         final int mSequenceNumber;
         final long mTimestamp;
         final long mWallTime;
+        @UserIdInt
+        final int mImeUserId;
         @NonNull
         final IBinder mImeToken;
+        final int mImeDisplayId;
         @NonNull
         final String mImeId;
         @StartInputReason
         final int mStartInputReason;
         final boolean mRestarting;
+        @UserIdInt
+        final int mTargetUserId;
+        final int mTargetDisplayId;
         @Nullable
         final IBinder mTargetWindow;
         @NonNull
@@ -682,17 +688,22 @@
         final int mTargetWindowSoftInputMode;
         final int mClientBindSequenceNumber;
 
-        StartInputInfo(@NonNull IBinder imeToken, @NonNull String imeId,
-                @StartInputReason int startInputReason, boolean restarting,
-                @Nullable IBinder targetWindow, @NonNull EditorInfo editorInfo,
-                @SoftInputModeFlags int targetWindowSoftInputMode, int clientBindSequenceNumber) {
+        StartInputInfo(@UserIdInt int imeUserId, @NonNull IBinder imeToken, int imeDisplayId,
+                @NonNull String imeId, @StartInputReason int startInputReason, boolean restarting,
+                @UserIdInt int targetUserId, int targetDisplayId, @Nullable IBinder targetWindow,
+                @NonNull EditorInfo editorInfo, @SoftInputModeFlags int targetWindowSoftInputMode,
+                int clientBindSequenceNumber) {
             mSequenceNumber = sSequenceNumber.getAndIncrement();
             mTimestamp = SystemClock.uptimeMillis();
             mWallTime = System.currentTimeMillis();
+            mImeUserId = imeUserId;
             mImeToken = imeToken;
+            mImeDisplayId = imeDisplayId;
             mImeId = imeId;
             mStartInputReason = startInputReason;
             mRestarting = restarting;
+            mTargetUserId = targetUserId;
+            mTargetDisplayId = targetDisplayId;
             mTargetWindow = targetWindow;
             mEditorInfo = editorInfo;
             mTargetWindowSoftInputMode = targetWindowSoftInputMode;
@@ -749,13 +760,19 @@
             int mSequenceNumber;
             long mTimestamp;
             long mWallTime;
+            @UserIdInt
+            int mImeUserId;
             @NonNull
             String mImeTokenString;
+            int mImeDisplayId;
             @NonNull
             String mImeId;
             @StartInputReason
             int mStartInputReason;
             boolean mRestarting;
+            @UserIdInt
+            int mTargetUserId;
+            int mTargetDisplayId;
             @NonNull
             String mTargetWindowString;
             @NonNull
@@ -772,12 +789,16 @@
                 mSequenceNumber = original.mSequenceNumber;
                 mTimestamp = original.mTimestamp;
                 mWallTime = original.mWallTime;
+                mImeUserId = original.mImeUserId;
                 // Intentionally convert to String so as not to keep a strong reference to a Binder
                 // object.
                 mImeTokenString = String.valueOf(original.mImeToken);
+                mImeDisplayId = original.mImeDisplayId;
                 mImeId = original.mImeId;
                 mStartInputReason = original.mStartInputReason;
                 mRestarting = original.mRestarting;
+                mTargetUserId = original.mTargetUserId;
+                mTargetDisplayId = original.mTargetDisplayId;
                 // Intentionally convert to String so as not to keep a strong reference to a Binder
                 // object.
                 mTargetWindowString = String.valueOf(original.mTargetWindow);
@@ -821,11 +842,15 @@
                         + " restarting=" + entry.mRestarting);
 
                 pw.print(prefix);
-                pw.println(" imeToken=" + entry.mImeTokenString + " [" + entry.mImeId + "]");
+                pw.print(" imeToken=" + entry.mImeTokenString + " [" + entry.mImeId + "]");
+                pw.print(" imeUserId=" + entry.mImeUserId);
+                pw.println(" imeDisplayId=" + entry.mImeDisplayId);
 
                 pw.print(prefix);
                 pw.println(" targetWin=" + entry.mTargetWindowString
                         + " [" + entry.mEditorInfo.packageName + "]"
+                        + " targetUserId=" + entry.mTargetUserId
+                        + " targetDisplayId=" + entry.mTargetDisplayId
                         + " clientBindSeq=" + entry.mClientBindSequenceNumber);
 
                 pw.print(prefix);
@@ -1904,9 +1929,10 @@
         }
 
         final Binder startInputToken = new Binder();
-        final StartInputInfo info = new StartInputInfo(mCurToken, mCurId, startInputReason,
-                !initial, mCurFocusedWindow, mCurAttribute, mCurFocusedWindowSoftInputMode,
-                mCurSeq);
+        final StartInputInfo info = new StartInputInfo(mSettings.getCurrentUserId(), mCurToken,
+                mCurTokenDisplayId, mCurId, startInputReason, !initial,
+                UserHandle.getUserId(mCurClient.uid), mCurClient.selfReportedDisplayId,
+                mCurFocusedWindow, mCurAttribute, mCurFocusedWindowSoftInputMode, mCurSeq);
         mImeTargetWindowMap.put(startInputToken, mCurFocusedWindow);
         mStartInputHistory.addEntry(info);
 
diff --git a/services/core/java/com/android/server/wm/AppWindowToken.java b/services/core/java/com/android/server/wm/AppWindowToken.java
index bcf6aba..727fb3b 100644
--- a/services/core/java/com/android/server/wm/AppWindowToken.java
+++ b/services/core/java/com/android/server/wm/AppWindowToken.java
@@ -1657,8 +1657,10 @@
             final ActivityManager.TaskSnapshot snapshot = snapshotCtrl.getSnapshot(
                     getTask().mTaskId, getTask().mUserId, false /* restoreFromDisk */,
                     false /* reducedResolution */);
-            mThumbnail = new AppWindowThumbnail(t, this, snapshot.getSnapshot(),
-                    true /* relative */);
+            if (snapshot != null) {
+                mThumbnail = new AppWindowThumbnail(t, this, snapshot.getSnapshot(),
+                        true /* relative */);
+            }
         }
     }
 
diff --git a/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenTests.java b/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenTests.java
index 069a609..e5e850a 100644
--- a/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/AppWindowTokenTests.java
@@ -62,7 +62,6 @@
  * Build/Install/Run:
  *  atest FrameworksServicesTests:AppWindowTokenTests
  */
-@FlakyTest(bugId = 68267650)
 @SmallTest
 @Presubmit
 public class AppWindowTokenTests extends WindowTestsBase {
@@ -79,6 +78,7 @@
         mTask = createTaskInStack(mStack, 0 /* userId */);
         mToken = WindowTestUtils.createTestAppWindowToken(mDisplayContent);
 
+        mToken.mSkipOnParentChanged = false;
         mTask.addChild(mToken, 0);
     }
 
@@ -303,6 +303,7 @@
         assertNoStartingWindow(mToken);
     }
 
+    @FlakyTest(detail = "Promote to presubmit when shown to be stable.")
     @Test
     public void testAddRemoveRace() {
         // There was once a race condition between adding and removing starting windows
@@ -387,6 +388,7 @@
         // bottom one.
         tokenTop.setVisibility(false, false);
         tokenBottom.transferStartingWindowFromHiddenAboveTokenIfNeeded();
+        waitUntilHandlersIdle();
 
         // Assert that the bottom window now has the starting window.
         assertNoStartingWindow(tokenTop);
diff --git a/services/tests/wmtests/src/com/android/server/wm/TestSystemServices.java b/services/tests/wmtests/src/com/android/server/wm/TestSystemServices.java
index 1c1fe29..e540b3a 100644
--- a/services/tests/wmtests/src/com/android/server/wm/TestSystemServices.java
+++ b/services/tests/wmtests/src/com/android/server/wm/TestSystemServices.java
@@ -61,7 +61,7 @@
 import org.mockito.invocation.InvocationOnMock;
 import org.mockito.quality.Strictness;
 
-import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.atomic.AtomicBoolean;
 
 /**
  * A Test utility class to create a mock {@link WindowManagerService} instance for tests.
@@ -71,6 +71,8 @@
     private static WindowManagerService sService;
     private static TestWindowManagerPolicy sPolicy;
 
+    static AtomicBoolean sCurrentMessagesProcessed = new AtomicBoolean(false);
+
     static void setUpWindowManagerService() {
         sMockitoSession = mockitoSession()
                 .spyStatic(LockGuard.class)
@@ -195,21 +197,23 @@
     }
 
     private static void waitHandlerIdle(Handler handler) {
-        if (!handler.hasMessagesOrCallbacks()) {
-            return;
-        }
-        final CountDownLatch latch = new CountDownLatch(1);
-        // Wait for delayed messages are processed.
-        handler.getLooper().getQueue().addIdleHandler(() -> {
-            if (handler.hasMessagesOrCallbacks()) {
-                return true; // keep idle handler.
+        synchronized (sCurrentMessagesProcessed) {
+            // Add a message to the handler queue and make sure it is fully processed before we move
+            // on. This makes sure all previous messages in the handler are fully processed vs. just
+            // popping them from the message queue.
+            sCurrentMessagesProcessed.set(false);
+            handler.post(() -> {
+                synchronized (sCurrentMessagesProcessed) {
+                    sCurrentMessagesProcessed.set(true);
+                    sCurrentMessagesProcessed.notifyAll();
+                }
+            });
+            while (!sCurrentMessagesProcessed.get()) {
+                try {
+                    sCurrentMessagesProcessed.wait();
+                } catch (InterruptedException e) {
+                }
             }
-            latch.countDown();
-            return false; // remove idle handler.
-        });
-        try {
-            latch.await();
-        } catch (InterruptedException e) {
         }
     }
 }
diff --git a/telephony/java/android/provider/Telephony.java b/telephony/java/android/provider/Telephony.java
index 4539ab3..a1c32b5 100644
--- a/telephony/java/android/provider/Telephony.java
+++ b/telephony/java/android/provider/Telephony.java
@@ -2717,6 +2717,41 @@
             Uri RCS_EVENT_QUERY_URI = Uri.withAppendedPath(CONTENT_AND_AUTHORITY,
                     RCS_EVENT_QUERY_URI_PATH);
         }
+
+        /**
+         * Allows RCS specific canonical address handling.
+         */
+        interface RcsCanonicalAddressHelper {
+            /**
+             * Returns the canonical address ID for a canonical address, if now row exists, this
+             * will add a row and return its ID. This helper works against the same table used by
+             * the SMS and MMS threads, but is accessible only by the phone process for use by RCS
+             * message storage.
+             *
+             * @throws IllegalArgumentException if unable to retrieve or create the canonical
+             *                                  address entry.
+             */
+            static long getOrCreateCanonicalAddressId(
+                    ContentResolver contentResolver, String canonicalAddress) {
+
+                Uri.Builder uriBuilder = CONTENT_AND_AUTHORITY.buildUpon();
+                uriBuilder.appendPath("canonical-address");
+                uriBuilder.appendQueryParameter("address", canonicalAddress);
+                Uri uri = uriBuilder.build();
+
+                try (Cursor cursor = contentResolver.query(uri, null, null, null)) {
+                    if (cursor != null && cursor.moveToFirst()) {
+                        return cursor.getLong(cursor.getColumnIndex(CanonicalAddressesColumns._ID));
+                    } else {
+                        Rlog.e(TAG, "getOrCreateCanonicalAddressId returned no rows");
+                    }
+                }
+
+                Rlog.e(TAG, "getOrCreateCanonicalAddressId failed");
+                throw new IllegalArgumentException(
+                        "Unable to find or allocate a canonical address ID");
+            }
+        }
     }
 
     /**