Ensure IMS calls are disconnected when WPS call is forced over CS.
When a WPS call is placed on the CS domain, ensure that we hangup any
ongoing calls on the IMS domain first.
Test: Added unit test to verify ImsPhoneCallTracker is asked to disconnect
all ongoing calls when a WPS call is placed over CS.
Test: Added unit test to verify ImsPhoneCallTracker is not asked to
disconnect all ongoing calls when a WPS call is placed over IMS.
Test: Manually overrode carrier config to ensure WPS calls go over CS,
started on device IMS call to another number. Then attempted to place a
WPS call. Verified that the ongoing IMS call disconnects and the WPS
call is placed.
Fixes: 172695501
Original change: https://android-review.googlesource.com/c/platform/frameworks/opt/telephony/+/1492301
Merged-In: I60382869482a78612a11b4a1672f0ba84f6068ed
Change-Id: I60382869482a78612a11b4a1672f0ba84f6068ed
(cherry picked from commit 28f1079976dea1cbc13822ec669a27b32905e486)
diff --git a/src/java/com/android/internal/telephony/GsmCdmaPhone.java b/src/java/com/android/internal/telephony/GsmCdmaPhone.java
index f64211b..52ce7bd 100644
--- a/src/java/com/android/internal/telephony/GsmCdmaPhone.java
+++ b/src/java/com/android/internal/telephony/GsmCdmaPhone.java
@@ -90,6 +90,7 @@
import com.android.internal.telephony.emergency.EmergencyNumberTracker;
import com.android.internal.telephony.gsm.GsmMmiCode;
import com.android.internal.telephony.gsm.SuppServiceNotification;
+import com.android.internal.telephony.imsphone.ImsPhoneCallTracker;
import com.android.internal.telephony.imsphone.ImsPhoneMmiCode;
import com.android.internal.telephony.metrics.VoiceCallSessionStats;
import com.android.internal.telephony.test.SimulatedRadioControl;
@@ -1367,6 +1368,12 @@
}
Phone.checkWfcWifiOnlyModeBeforeDial(mImsPhone, mPhoneId, mContext);
+ if (imsPhone != null && !allowWpsOverIms && !useImsForCall && isWpsCall
+ && imsPhone.getCallTracker() instanceof ImsPhoneCallTracker) {
+ logi("WPS call placed over CS; disconnecting all IMS calls..");
+ ImsPhoneCallTracker tracker = (ImsPhoneCallTracker) imsPhone.getCallTracker();
+ tracker.hangupAllConnections();
+ }
if ((useImsForCall && (!isMmiCode || isPotentialUssdCode))
|| (isMmiCode && useImsForUt)
diff --git a/src/java/com/android/internal/telephony/imsphone/ImsPhoneCallTracker.java b/src/java/com/android/internal/telephony/imsphone/ImsPhoneCallTracker.java
index 15e2d28..ce05675 100755
--- a/src/java/com/android/internal/telephony/imsphone/ImsPhoneCallTracker.java
+++ b/src/java/com/android/internal/telephony/imsphone/ImsPhoneCallTracker.java
@@ -1025,6 +1025,20 @@
sendImsServiceStateIntent(ImsManager.ACTION_IMS_SERVICE_DOWN);
}
+ /**
+ * Requests modem to hang up all connections.
+ */
+ public void hangupAllConnections() {
+ getConnections().stream().forEach(c -> {
+ logi("Disconnecting callId = " + c.getTelecomCallId());
+ try {
+ c.hangup();
+ } catch (CallStateException e) {
+ loge("Failed to disconnet call...");
+ }
+ });
+ }
+
private void sendImsServiceStateIntent(String intentAction) {
Intent intent = new Intent(intentAction);
intent.putExtra(ImsManager.EXTRA_PHONE_ID, mPhone.getPhoneId());
diff --git a/tests/telephonytests/src/com/android/internal/telephony/GsmCdmaPhoneTest.java b/tests/telephonytests/src/com/android/internal/telephony/GsmCdmaPhoneTest.java
index 7ad41c2..0dd9121 100644
--- a/tests/telephonytests/src/com/android/internal/telephony/GsmCdmaPhoneTest.java
+++ b/tests/telephonytests/src/com/android/internal/telephony/GsmCdmaPhoneTest.java
@@ -43,6 +43,7 @@
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
import android.content.Intent;
import android.content.SharedPreferences;
@@ -494,6 +495,42 @@
@Test
@SmallTest
+ public void testWpsDialOverCs() throws Exception {
+ try {
+ setupForWpsCallTest();
+
+ mContextFixture.getCarrierConfigBundle().putBoolean(
+ CarrierConfigManager.KEY_SUPPORT_WPS_OVER_IMS_BOOL, false);
+
+ Connection connection = mPhoneUT.dial("*27216505551212",
+ new PhoneInternalInterface.DialArgs.Builder().build());
+ verify(mCT).dialGsm("*27216505551212", null, null);
+ verify(mImsCT).hangupAllConnections();
+ } catch (CallStateException e) {
+ fail();
+ }
+ }
+
+ @Test
+ @SmallTest
+ public void testWpsDialOverIms() throws Exception {
+ try {
+ setupForWpsCallTest();
+
+ mContextFixture.getCarrierConfigBundle().putBoolean(
+ CarrierConfigManager.KEY_SUPPORT_WPS_OVER_IMS_BOOL, true);
+
+ Connection connection = mPhoneUT.dial("*27216505551212",
+ new PhoneInternalInterface.DialArgs.Builder().build());
+ verify(mCT).dialGsm("*27216505551212", null, null);
+ verify(mImsCT, never()).hangupAllConnections();
+ } catch (CallStateException e) {
+ fail();
+ }
+ }
+
+ @Test
+ @SmallTest
public void testHandlePinMmi() {
assertFalse(mPhoneUT.handlePinMmi("1234567890"));
}
@@ -1386,4 +1423,15 @@
verify(mMockCi).getRadioCapability(captor.capture());
assertEquals(captor.getValue().what, Phone.EVENT_GET_RADIO_CAPABILITY);
}
+
+ private void setupForWpsCallTest() throws Exception {
+ mSST.mSS = mServiceState;
+ doReturn(ServiceState.STATE_IN_SERVICE).when(mServiceState).getState();
+ when(mImsPhone.getCallTracker()).thenReturn(mImsCT);
+ mCT.mForegroundCall = mGsmCdmaCall;
+ mCT.mBackgroundCall = mGsmCdmaCall;
+ mCT.mRingingCall = mGsmCdmaCall;
+ doReturn(GsmCdmaCall.State.IDLE).when(mGsmCdmaCall).getState();
+ replaceInstance(Phone.class, "mImsPhone", mPhoneUT, mImsPhone);
+ }
}