Self-Managed Incoming Call Disambiguation UX.

- Handle auto-disconnect of foreground call when answering a self-managed
call.
- Enforce restriction that the PhoneAccount associated with a self-managed
CS must have a label which is the app's name.
- Ensure self-managed phone accounts can't be registered with
call provider, connection manager, or sim sub capabilities.
- Add "incoming call" UX which is shown when a new incoming call from a
self-managed CS comes in and there is an existing call for another CS.

Test: Unit, manual
Bug: 34159263
Change-Id: I371be9baa6f56c77aa83349977c0131f0e319047
diff --git a/src/com/android/server/telecom/PhoneAccountRegistrar.java b/src/com/android/server/telecom/PhoneAccountRegistrar.java
index 4fe6ed6..ea82d52 100644
--- a/src/com/android/server/telecom/PhoneAccountRegistrar.java
+++ b/src/com/android/server/telecom/PhoneAccountRegistrar.java
@@ -122,6 +122,14 @@
         public void onSimCallManagerChanged(PhoneAccountRegistrar registrar) {}
     }
 
+    /**
+     * Abstracts away dependency on the {@link PackageManager} required to fetch the label for an
+     * app.
+     */
+    public interface AppLabelProxy {
+        CharSequence getAppLabel(String packageName);
+    }
+
     private static final String FILE_NAME = "phone-account-registrar-state.xml";
     @VisibleForTesting
     public static final int EXPECTED_STATE_VERSION = 9;
@@ -135,6 +143,7 @@
     private final UserManager mUserManager;
     private final SubscriptionManager mSubscriptionManager;
     private final DefaultDialerCache mDefaultDialerCache;
+    private final AppLabelProxy mAppLabelProxy;
     private State mState;
     private UserHandle mCurrentUserHandle;
     private interface PhoneAccountRegistrarWriteLock {}
@@ -142,21 +151,15 @@
             new PhoneAccountRegistrarWriteLock() {};
 
     @VisibleForTesting
-    public PhoneAccountRegistrar(Context context, DefaultDialerCache defaultDialerCache) {
-        this(context, FILE_NAME, defaultDialerCache);
+    public PhoneAccountRegistrar(Context context, DefaultDialerCache defaultDialerCache,
+                                 AppLabelProxy appLabelProxy) {
+        this(context, FILE_NAME, defaultDialerCache, appLabelProxy);
     }
 
     @VisibleForTesting
     public PhoneAccountRegistrar(Context context, String fileName,
-            DefaultDialerCache defaultDialerCache) {
-        // TODO: This file path is subject to change -- it is storing the phone account registry
-        // state file in the path /data/system/users/0/, which is likely not correct in a
-        // multi-user setting.
-        /** UNCOMMENT_FOR_MOVE_TO_SYSTEM_SERVICE
-        String filePath = Environment.getUserSystemDirectory(UserHandle.myUserId()).
-                getAbsolutePath();
-        mAtomicFile = new AtomicFile(new File(filePath, fileName));
-         UNCOMMENT_FOR_MOVE_TO_SYSTEM_SERVICE */
+            DefaultDialerCache defaultDialerCache, AppLabelProxy appLabelProxy) {
+
         mAtomicFile = new AtomicFile(new File(context.getFilesDir(), fileName));
 
         mState = new State();
@@ -164,6 +167,7 @@
         mUserManager = UserManager.get(context);
         mDefaultDialerCache = defaultDialerCache;
         mSubscriptionManager = SubscriptionManager.from(mContext);
+        mAppLabelProxy = appLabelProxy;
         mCurrentUserHandle = Process.myUserHandle();
         read();
     }
@@ -640,6 +644,27 @@
             Log.i(this, "New phone account registered: " + account);
         }
 
+        // When registering a self-managed PhoneAccount we enforce the rule that the label that the
+        // app uses is also its phone account label.  Also ensure it does not attempt to declare
+        // itself as a sim acct, call manager or call provider.
+        if (account.hasCapabilities(PhoneAccount.CAPABILITY_SELF_MANAGED)) {
+            // Turn off bits we don't want to be able to set (TelecomServiceImpl protects against
+            // this but we'll also prevent it from happening here, just to be safe).
+            int newCapabilities = account.getCapabilities() &
+                    ~(PhoneAccount.CAPABILITY_CALL_PROVIDER |
+                        PhoneAccount.CAPABILITY_CONNECTION_MANAGER |
+                        PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
+
+            // Ensure name is correct.
+            CharSequence newLabel = mAppLabelProxy.getAppLabel(
+                    account.getAccountHandle().getComponentName().getPackageName());
+
+            account = account.toBuilder()
+                    .setLabel(newLabel)
+                    .setCapabilities(newCapabilities)
+                    .build();
+        }
+
         mState.accounts.add(account);
         // Set defaults and replace based on the group Id.
         maybeReplaceOldAccount(account);