Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d0b67760 authored by Aishwarya Mallampati's avatar Aishwarya Mallampati Committed by Android (Google) Code Review
Browse files

Merge "Timeout is not needed for E911 call if carrier is not in service." into 24D1-dev

parents fb14e282 c2c6c619
Loading
Loading
Loading
Loading
+22 −3
Original line number Diff line number Diff line
@@ -16,21 +16,27 @@

package com.android.server.telecom;

import static com.android.internal.telephony.flags.Flags.carrierEnabledSatelliteFlag;

import android.content.Context;
import android.os.Handler;
import android.os.Looper;
import android.telecom.Log;
import android.telecom.Logging.Runnable;
import android.telecom.PhoneAccount;
import android.telecom.PhoneAccountHandle;
import android.telephony.TelephonyManager;

import com.android.internal.annotations.VisibleForTesting;

import java.util.Collection;
import java.util.Objects;

/**
 * Registers a timeout for a call and disconnects the call when the timeout expires.
 */
final class CreateConnectionTimeout extends Runnable {
@VisibleForTesting
public final class CreateConnectionTimeout extends Runnable {
    private final Context mContext;
    private final PhoneAccountRegistrar mPhoneAccountRegistrar;
    private final ConnectionServiceWrapper mConnectionService;
@@ -39,7 +45,8 @@ final class CreateConnectionTimeout extends Runnable {
    private boolean mIsRegistered;
    private boolean mIsCallTimedOut;

    CreateConnectionTimeout(Context context, PhoneAccountRegistrar phoneAccountRegistrar,
    @VisibleForTesting
    public CreateConnectionTimeout(Context context, PhoneAccountRegistrar phoneAccountRegistrar,
            ConnectionServiceWrapper service, Call call) {
        super("CCT", null /*lock*/);
        mContext = context;
@@ -48,7 +55,8 @@ final class CreateConnectionTimeout extends Runnable {
        mCall = call;
    }

    boolean isTimeoutNeededForCall(Collection<PhoneAccountHandle> accounts,
    @VisibleForTesting
    public boolean isTimeoutNeededForCall(Collection<PhoneAccountHandle> accounts,
            PhoneAccountHandle currentAccount) {
        // Non-emergency calls timeout automatically at the radio layer. No need for a timeout here.
        if (!mCall.isEmergencyCall()) {
@@ -75,6 +83,17 @@ final class CreateConnectionTimeout extends Runnable {
            return false;
        }

        // Timeout is not required if carrier is not in service.
        if (carrierEnabledSatelliteFlag() && connectionManager != null) {
            PhoneAccount account = mPhoneAccountRegistrar.getPhoneAccount(connectionManager,
                    connectionManager.getUserHandle());
            if (account.hasCapabilities(PhoneAccount.CAPABILITY_SUPPORTS_VOICE_CALLING_INDICATIONS)
                    && !account.hasCapabilities(PhoneAccount.CAPABILITY_VOICE_CALLING_AVAILABLE)) {
                Log.d(this, "isTimeoutNeededForCall, carrier is not in service.");
                return false;
            }
        }

        Log.i(this, "isTimeoutNeededForCall, returning true");
        return true;
    }
+117 −0
Original line number Diff line number Diff line
@@ -16,6 +16,9 @@

package com.android.server.telecom.tests;

import static junit.framework.Assert.assertFalse;
import static junit.framework.Assert.assertTrue;

import static org.junit.Assert.fail;
import static org.mockito.ArgumentMatchers.anyBoolean;
import static org.mockito.ArgumentMatchers.anyList;
@@ -35,6 +38,7 @@ import android.graphics.drawable.Icon;
import android.net.Uri;
import android.os.Binder;
import android.os.UserHandle;
import android.platform.test.flag.junit.SetFlagsRule;
import android.telecom.DisconnectCause;
import android.telecom.PhoneAccount;
import android.telecom.PhoneAccountHandle;
@@ -42,6 +46,7 @@ import android.telephony.SubscriptionManager;

import androidx.test.filters.SmallTest;

import com.android.internal.telephony.flags.Flags;
import com.android.server.telecom.Call;
import com.android.server.telecom.CallIdMapper;
import com.android.server.telecom.ConnectionServiceFocusManager;
@@ -49,11 +54,13 @@ import com.android.server.telecom.ConnectionServiceRepository;
import com.android.server.telecom.ConnectionServiceWrapper;
import com.android.server.telecom.CreateConnectionProcessor;
import com.android.server.telecom.CreateConnectionResponse;
import com.android.server.telecom.CreateConnectionTimeout;
import com.android.server.telecom.PhoneAccountRegistrar;
import com.android.server.telecom.flags.FeatureFlags;

import org.junit.After;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
@@ -73,6 +80,7 @@ import java.util.UUID;
 */
@RunWith(JUnit4.class)
public class CreateConnectionProcessorTest extends TelecomTestCase {
    @Rule public final SetFlagsRule mSetFlagsRule = new SetFlagsRule();

    private static final String TEST_PACKAGE = "com.android.server.telecom.tests";
    private static final String TEST_CLASS =
@@ -91,6 +99,7 @@ public class CreateConnectionProcessorTest extends TelecomTestCase {
    ConnectionServiceFocusManager mConnectionServiceFocusManager;

    CreateConnectionProcessor mTestCreateConnectionProcessor;
    CreateConnectionTimeout mTestCreateConnectionTimeout;

    private ArrayList<PhoneAccount> phoneAccounts;
    private HashMap<Integer,Integer> mSubToSlot;
@@ -144,6 +153,11 @@ public class CreateConnectionProcessorTest extends TelecomTestCase {
                .thenReturn(phoneAccounts);
        when(mMockCall.getAssociatedUser()).
                thenReturn(Binder.getCallingUserHandle());

        mTestCreateConnectionTimeout = new CreateConnectionTimeout(mContext, mMockAccountRegistrar,
                makeConnectionServiceWrapper(), mMockCall);

        mSetFlagsRule.enableFlags(Flags.FLAG_CARRIER_ENABLED_SATELLITE_FLAG);
    }

    @Override
@@ -707,6 +721,109 @@ public class CreateConnectionProcessorTest extends TelecomTestCase {
        }
    }

    @Test
    public void testIsTimeoutNeededForCall_nonEmergencyCall() {
        when(mMockCall.isEmergencyCall()).thenReturn(false);

        assertFalse(mTestCreateConnectionTimeout.isTimeoutNeededForCall(null, null));
    }

    @Test
    public void testIsTimeoutNeededForCall_noConnectionManager() {
        when(mMockCall.isEmergencyCall()).thenReturn(true);
        List<PhoneAccountHandle> phoneAccountHandles = new ArrayList<>();
        // Put in a regular phone account handle
        PhoneAccount regularAccount = makePhoneAccount("tel_acct1",
                PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
        phoneAccountHandles.add(regularAccount.getAccountHandle());
        // Create a connection manager for the call and do not include in phoneAccountHandles
        createNewConnectionManagerPhoneAccountForCall(mMockCall, "cm_acct", 0);

        assertFalse(mTestCreateConnectionTimeout.isTimeoutNeededForCall(phoneAccountHandles, null));
    }

    @Test
    public void testIsTimeoutNeededForCall_usingConnectionManager() {
        when(mMockCall.isEmergencyCall()).thenReturn(true);
        List<PhoneAccountHandle> phoneAccountHandles = new ArrayList<>();
        // Put in a regular phone account handle
        PhoneAccount regularAccount = makePhoneAccount("tel_acct1",
                PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
        phoneAccountHandles.add(regularAccount.getAccountHandle());
        // Create a connection manager for the call and include it in phoneAccountHandles
        PhoneAccount callManagerPA = createNewConnectionManagerPhoneAccountForCall(mMockCall,
                "cm_acct", 0);
        phoneAccountHandles.add(callManagerPA.getAccountHandle());

        assertFalse(mTestCreateConnectionTimeout.isTimeoutNeededForCall(
                phoneAccountHandles, callManagerPA.getAccountHandle()));
    }

    @Test
    public void testIsTimeoutNeededForCall_NotSystemSimCallManager() {
        when(mMockCall.isEmergencyCall()).thenReturn(true);
        List<PhoneAccountHandle> phoneAccountHandles = new ArrayList<>();
        // Put in a regular phone account handle
        PhoneAccount regularAccount = makePhoneAccount("tel_acct1",
                PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
        phoneAccountHandles.add(regularAccount.getAccountHandle());
        // Create a connection manager for the call and include it in phoneAccountHandles
        PhoneAccount callManagerPA = createNewConnectionManagerPhoneAccountForCall(mMockCall,
                "cm_acct", 0);
        phoneAccountHandles.add(callManagerPA.getAccountHandle());

        assertFalse(mTestCreateConnectionTimeout.isTimeoutNeededForCall(phoneAccountHandles, null));
    }

    @Test
    public void testIsTimeoutNeededForCall_carrierNotInService() {
        when(mMockCall.isEmergencyCall()).thenReturn(true);
        when(mMockAccountRegistrar.getSystemSimCallManagerComponent()).thenReturn(
                new ComponentName(TEST_PACKAGE, TEST_CLASS));

        List<PhoneAccountHandle> phoneAccountHandles = new ArrayList<>();
        // Put in a regular phone account handle
        PhoneAccount regularAccount = makePhoneAccount("tel_acct1",
                PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
        phoneAccountHandles.add(regularAccount.getAccountHandle());
        // Create a connection manager for the call and include it in phoneAccountHandles
        int capability = PhoneAccount.CAPABILITY_SUPPORTS_VOICE_CALLING_INDICATIONS;
        PhoneAccount callManagerPA = createNewConnectionManagerPhoneAccountForCall(mMockCall,
                "cm_acct", capability);
        PhoneAccount phoneAccountWithoutService = makeQuickAccount("cm_acct", capability, null);
        when(mMockAccountRegistrar.getPhoneAccount(callManagerPA.getAccountHandle(),
                callManagerPA.getAccountHandle().getUserHandle()))
                .thenReturn(phoneAccountWithoutService);
        phoneAccountHandles.add(callManagerPA.getAccountHandle());

        assertFalse(mTestCreateConnectionTimeout.isTimeoutNeededForCall(phoneAccountHandles, null));
    }

    @Test
    public void testIsTimeoutNeededForCall() {
        when(mMockCall.isEmergencyCall()).thenReturn(true);
        when(mMockAccountRegistrar.getSystemSimCallManagerComponent()).thenReturn(
                new ComponentName(TEST_PACKAGE, TEST_CLASS));

        List<PhoneAccountHandle> phoneAccountHandles = new ArrayList<>();
        // Put in a regular phone account handle
        PhoneAccount regularAccount = makePhoneAccount("tel_acct1",
                PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION);
        phoneAccountHandles.add(regularAccount.getAccountHandle());
        // Create a connection manager for the call and include it in phoneAccountHandles
        int capability = PhoneAccount.CAPABILITY_SUPPORTS_VOICE_CALLING_INDICATIONS
                | PhoneAccount.CAPABILITY_VOICE_CALLING_AVAILABLE;
        PhoneAccount callManagerPA = createNewConnectionManagerPhoneAccountForCall(mMockCall,
                "cm_acct", capability);
        PhoneAccount phoneAccountWithService = makeQuickAccount("cm_acct", capability, null);
        when(mMockAccountRegistrar.getPhoneAccount(callManagerPA.getAccountHandle(),
                callManagerPA.getAccountHandle().getUserHandle()))
                .thenReturn(phoneAccountWithService);
        phoneAccountHandles.add(callManagerPA.getAccountHandle());

        assertTrue(mTestCreateConnectionTimeout.isTimeoutNeededForCall(phoneAccountHandles, null));
    }

    /**
     * Generates random phone accounts.
     * @param seed random seed to use for random UUIDs; passed in for determinism.