diff options
author | Brad Ebinger <breadley@google.com> | 2020-09-23 17:00:10 -0700 |
---|---|---|
committer | Brad Ebinger <breadley@google.com> | 2020-10-21 13:25:20 -0700 |
commit | 4b14954fb45bfac3bcf695ff05a7a2e584204131 (patch) | |
tree | 8b024c705f8157cfe12b40c0ac4f048fb273e0f1 | |
parent | c50aeb319a64c9a0cfd715fc30f02bb63d8bdb1a (diff) |
Add isSupported implementation for SipTransport
Add implementation for SipDelegateManager#isSupported as well
as CTS tests.
Bug: 154763999
Test: atest CtsTelephonyTestCases
Merged-In: I7fbd39a8ff17c4e947fdbcca148857684faa3252
Change-Id: I7fbd39a8ff17c4e947fdbcca148857684faa3252
-rw-r--r-- | api/current.txt | 1 | ||||
-rwxr-xr-x | api/system-current.txt | 15 | ||||
-rw-r--r-- | non-updatable-api/current.txt | 1 | ||||
-rw-r--r-- | non-updatable-api/system-current.txt | 15 | ||||
-rw-r--r-- | telephony/api/system-current.txt | 15 | ||||
-rw-r--r-- | telephony/java/android/telephony/CarrierConfigManager.java | 15 | ||||
-rw-r--r-- | telephony/java/android/telephony/ImsManager.java | 21 | ||||
-rw-r--r-- | telephony/java/android/telephony/ims/ImsService.java | 12 | ||||
-rw-r--r-- | telephony/java/android/telephony/ims/SipDelegateManager.java | 93 | ||||
-rw-r--r-- | telephony/java/android/telephony/ims/aidl/IImsRcsController.aidl | 3 | ||||
-rw-r--r-- | telephony/java/android/telephony/ims/stub/SipTransportImplBase.java | 5 |
11 files changed, 191 insertions, 5 deletions
diff --git a/api/current.txt b/api/current.txt index 22b8c456f655..90c0eab439c4 100644 --- a/api/current.txt +++ b/api/current.txt @@ -46887,6 +46887,7 @@ package android.telephony { } public static final class CarrierConfigManager.Ims { + field public static final String KEY_IMS_SINGLE_REGISTRATION_REQUIRED_BOOL = "ims.ims_single_registration_required_bool"; field public static final String KEY_PREFIX = "ims."; field public static final String KEY_WIFI_OFF_DEFERRING_TIME_MILLIS_INT = "ims.wifi_off_deferring_time_millis_int"; } diff --git a/api/system-current.txt b/api/system-current.txt index 6475d81067cd..11b2828e6247 100755 --- a/api/system-current.txt +++ b/api/system-current.txt @@ -11904,6 +11904,10 @@ package android.telephony.ims { field @NonNull public static final android.os.Parcelable.Creator<android.telephony.ims.ImsExternalCallState> CREATOR; } + public class ImsManager { + method @NonNull public android.telephony.ims.SipDelegateManager getSipDelegateManager(int); + } + public class ImsMmTelManager implements android.telephony.ims.RegistrationManager { method @Deprecated @NonNull @RequiresPermission(anyOf={android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE, android.Manifest.permission.READ_PRECISE_PHONE_STATE}) public static android.telephony.ims.ImsMmTelManager createForSubscriptionId(int); method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public void getFeatureState(@NonNull java.util.concurrent.Executor, @NonNull java.util.function.Consumer<java.lang.Integer>) throws android.telephony.ims.ImsException; @@ -11939,10 +11943,13 @@ package android.telephony.ims { method public void disableIms(int); method public void enableIms(int); method public android.telephony.ims.stub.ImsConfigImplBase getConfig(int); + method public long getImsServiceCapabilities(); method public android.telephony.ims.stub.ImsRegistrationImplBase getRegistration(int); + method @Nullable public android.telephony.ims.stub.SipTransportImplBase getSipTransport(int); method public final void onUpdateSupportedImsFeatures(android.telephony.ims.stub.ImsFeatureConfiguration) throws android.os.RemoteException; method public android.telephony.ims.stub.ImsFeatureConfiguration querySupportedImsFeatures(); method public void readyForFeatureCreation(); + field public static final long CAPABILITY_SIP_DELEGATE_CREATION = 2L; // 0x2L } public final class ImsSsData implements android.os.Parcelable { @@ -12188,6 +12195,10 @@ package android.telephony.ims { method @RequiresPermission(android.Manifest.permission.MODIFY_PHONE_STATE) public void setUceSettingEnabled(boolean) throws android.telephony.ims.ImsException; } + public class SipDelegateManager { + method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public boolean isSupported() throws android.telephony.ims.ImsException; + } + } package android.telephony.ims.feature { @@ -12437,6 +12448,10 @@ package android.telephony.ims.stub { method public int updateColr(int); } + public class SipTransportImplBase { + ctor public SipTransportImplBase(@NonNull java.util.concurrent.Executor); + } + } package android.telephony.mbms { diff --git a/non-updatable-api/current.txt b/non-updatable-api/current.txt index da3d0f7ff059..e7306367daf5 100644 --- a/non-updatable-api/current.txt +++ b/non-updatable-api/current.txt @@ -45055,6 +45055,7 @@ package android.telephony { } public static final class CarrierConfigManager.Ims { + field public static final String KEY_IMS_SINGLE_REGISTRATION_REQUIRED_BOOL = "ims.ims_single_registration_required_bool"; field public static final String KEY_PREFIX = "ims."; field public static final String KEY_WIFI_OFF_DEFERRING_TIME_MILLIS_INT = "ims.wifi_off_deferring_time_millis_int"; } diff --git a/non-updatable-api/system-current.txt b/non-updatable-api/system-current.txt index 7d5d0a65d43e..515d368db9e2 100644 --- a/non-updatable-api/system-current.txt +++ b/non-updatable-api/system-current.txt @@ -10786,6 +10786,10 @@ package android.telephony.ims { field @NonNull public static final android.os.Parcelable.Creator<android.telephony.ims.ImsExternalCallState> CREATOR; } + public class ImsManager { + method @NonNull public android.telephony.ims.SipDelegateManager getSipDelegateManager(int); + } + public class ImsMmTelManager implements android.telephony.ims.RegistrationManager { method @Deprecated @NonNull @RequiresPermission(anyOf={android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE, android.Manifest.permission.READ_PRECISE_PHONE_STATE}) public static android.telephony.ims.ImsMmTelManager createForSubscriptionId(int); method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public void getFeatureState(@NonNull java.util.concurrent.Executor, @NonNull java.util.function.Consumer<java.lang.Integer>) throws android.telephony.ims.ImsException; @@ -10821,10 +10825,13 @@ package android.telephony.ims { method public void disableIms(int); method public void enableIms(int); method public android.telephony.ims.stub.ImsConfigImplBase getConfig(int); + method public long getImsServiceCapabilities(); method public android.telephony.ims.stub.ImsRegistrationImplBase getRegistration(int); + method @Nullable public android.telephony.ims.stub.SipTransportImplBase getSipTransport(int); method public final void onUpdateSupportedImsFeatures(android.telephony.ims.stub.ImsFeatureConfiguration) throws android.os.RemoteException; method public android.telephony.ims.stub.ImsFeatureConfiguration querySupportedImsFeatures(); method public void readyForFeatureCreation(); + field public static final long CAPABILITY_SIP_DELEGATE_CREATION = 2L; // 0x2L } public final class ImsSsData implements android.os.Parcelable { @@ -11070,6 +11077,10 @@ package android.telephony.ims { method @RequiresPermission(android.Manifest.permission.MODIFY_PHONE_STATE) public void setUceSettingEnabled(boolean) throws android.telephony.ims.ImsException; } + public class SipDelegateManager { + method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public boolean isSupported() throws android.telephony.ims.ImsException; + } + } package android.telephony.ims.feature { @@ -11319,6 +11330,10 @@ package android.telephony.ims.stub { method public int updateColr(int); } + public class SipTransportImplBase { + ctor public SipTransportImplBase(@NonNull java.util.concurrent.Executor); + } + } package android.telephony.mbms { diff --git a/telephony/api/system-current.txt b/telephony/api/system-current.txt index 5ad377273b90..f4b7b509be56 100644 --- a/telephony/api/system-current.txt +++ b/telephony/api/system-current.txt @@ -1361,6 +1361,10 @@ package android.telephony.ims { field @NonNull public static final android.os.Parcelable.Creator<android.telephony.ims.ImsExternalCallState> CREATOR; } + public class ImsManager { + method @NonNull public android.telephony.ims.SipDelegateManager getSipDelegateManager(int); + } + public class ImsMmTelManager implements android.telephony.ims.RegistrationManager { method @Deprecated @NonNull @RequiresPermission(anyOf={android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE, android.Manifest.permission.READ_PRECISE_PHONE_STATE}) public static android.telephony.ims.ImsMmTelManager createForSubscriptionId(int); method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public void getFeatureState(@NonNull java.util.concurrent.Executor, @NonNull java.util.function.Consumer<java.lang.Integer>) throws android.telephony.ims.ImsException; @@ -1396,10 +1400,13 @@ package android.telephony.ims { method public void disableIms(int); method public void enableIms(int); method public android.telephony.ims.stub.ImsConfigImplBase getConfig(int); + method public long getImsServiceCapabilities(); method public android.telephony.ims.stub.ImsRegistrationImplBase getRegistration(int); + method @Nullable public android.telephony.ims.stub.SipTransportImplBase getSipTransport(int); method public final void onUpdateSupportedImsFeatures(android.telephony.ims.stub.ImsFeatureConfiguration) throws android.os.RemoteException; method public android.telephony.ims.stub.ImsFeatureConfiguration querySupportedImsFeatures(); method public void readyForFeatureCreation(); + field public static final long CAPABILITY_SIP_DELEGATE_CREATION = 2L; // 0x2L } public final class ImsSsData implements android.os.Parcelable { @@ -1645,6 +1652,10 @@ package android.telephony.ims { method @RequiresPermission(android.Manifest.permission.MODIFY_PHONE_STATE) public void setUceSettingEnabled(boolean) throws android.telephony.ims.ImsException; } + public class SipDelegateManager { + method @RequiresPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE) public boolean isSupported() throws android.telephony.ims.ImsException; + } + } package android.telephony.ims.feature { @@ -1894,6 +1905,10 @@ package android.telephony.ims.stub { method public int updateColr(int); } + public class SipTransportImplBase { + ctor public SipTransportImplBase(@NonNull java.util.concurrent.Executor); + } + } package android.telephony.mbms { diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java index a4f48af93a8d..88a700e49a98 100644 --- a/telephony/java/android/telephony/CarrierConfigManager.java +++ b/telephony/java/android/telephony/CarrierConfigManager.java @@ -3785,11 +3785,26 @@ public class CarrierConfigManager { public static final String KEY_WIFI_OFF_DEFERRING_TIME_MILLIS_INT = KEY_PREFIX + "wifi_off_deferring_time_millis_int"; + /** + * A boolean flag specifying whether or not this carrier requires one IMS registration for + * all IMS services (MMTEL and RCS). + * <p> + * If set to {@code true}, the IMS Service must use one IMS registration for all IMS + * services. If set to {@code false}, IMS services may use separate IMS registrations for + * MMTEL and RCS. + * <p> + * The default value for this configuration is {@code false}. + * @see android.telephony.ims.SipDelegateManager + */ + public static final String KEY_IMS_SINGLE_REGISTRATION_REQUIRED_BOOL = + KEY_PREFIX + "ims_single_registration_required_bool"; + private Ims() {} private static PersistableBundle getDefaults() { PersistableBundle defaults = new PersistableBundle(); defaults.putInt(KEY_WIFI_OFF_DEFERRING_TIME_MILLIS_INT, 4000); + defaults.putBoolean(KEY_IMS_SINGLE_REGISTRATION_REQUIRED_BOOL, false); return defaults; } } diff --git a/telephony/java/android/telephony/ImsManager.java b/telephony/java/android/telephony/ImsManager.java index 3984bd769edd..28feab27a794 100644 --- a/telephony/java/android/telephony/ImsManager.java +++ b/telephony/java/android/telephony/ImsManager.java @@ -19,6 +19,7 @@ package android.telephony.ims; import android.annotation.NonNull; import android.annotation.SdkConstant; import android.annotation.SuppressLint; +import android.annotation.SystemApi; import android.annotation.SystemService; import android.content.Context; import android.telephony.SubscriptionManager; @@ -125,4 +126,24 @@ public class ImsManager { return new ImsMmTelManager(subscriptionId); } + + /** + * Create an instance of SipDelegateManager for the subscription id specified. + * <p> + * Used for RCS single registration cases, where an IMS application needs to forward SIP + * traffic through the device's IMS service. + * @param subscriptionId The ID of the subscription that this SipDelegateManager will use. + * @throws IllegalArgumentException if the subscription is invalid. + * @return a SipDelegateManager instance for the specified subscription ID. + * @hide + */ + @SystemApi + @NonNull + public SipDelegateManager getSipDelegateManager(int subscriptionId) { + if (!SubscriptionManager.isValidSubscriptionId(subscriptionId)) { + throw new IllegalArgumentException("Invalid subscription ID: " + subscriptionId); + } + + return new SipDelegateManager(mContext, subscriptionId); + } } diff --git a/telephony/java/android/telephony/ims/ImsService.java b/telephony/java/android/telephony/ims/ImsService.java index c806d5c8ed3a..9ab5aeb9c34c 100644 --- a/telephony/java/android/telephony/ims/ImsService.java +++ b/telephony/java/android/telephony/ims/ImsService.java @@ -18,6 +18,7 @@ package android.telephony.ims; import android.annotation.LongDef; import android.annotation.Nullable; +import android.annotation.SuppressLint; import android.annotation.SystemApi; import android.app.Service; import android.content.Intent; @@ -125,7 +126,6 @@ public class ImsService extends Service { * {@link #getImsServiceCapabilities()}, {@link #getSipTransport(int)} must not return null, and * this ImsService MUST report the ability to create both {@link ImsFeature#FEATURE_MMTEL} and * {@link ImsFeature#FEATURE_RCS} features. - * @hide */ public static final long CAPABILITY_SIP_DELEGATE_CREATION = 1 << 1; @@ -423,9 +423,12 @@ public class ImsService extends Service { * <p> * This should be a static configuration and should not change at runtime. * @return The optional static capabilities of this ImsService implementation. - * @hide */ + // ImsService follows a different convention, since it is a stub class. The on* methods are + // final and call back into the framework with a state update. + @SuppressLint("OnNameExpected") public @ImsServiceCapability long getImsServiceCapabilities() { + // Stub implementation to be implemented by ImsService. return 0L; } @@ -513,9 +516,12 @@ public class ImsService extends Service { * supported for this ImsService. * @param slotId The slot that is associated with the SipTransport implementation. * @return the SipTransport implementation for the specified slot. - * @hide Keep this hidden until there is something to expose in SipTransport. */ + // ImsService follows a different convention, since it is a stub class. The on* methods are + // final and call back into the framework with a state update. + @SuppressLint("OnNameExpected") public @Nullable SipTransportImplBase getSipTransport(int slotId) { + // Stub implementation for ImsServices that do not support SipTransport. return null; } diff --git a/telephony/java/android/telephony/ims/SipDelegateManager.java b/telephony/java/android/telephony/ims/SipDelegateManager.java new file mode 100644 index 000000000000..82c8a9cd58f4 --- /dev/null +++ b/telephony/java/android/telephony/ims/SipDelegateManager.java @@ -0,0 +1,93 @@ +/* + * Copyright (C) 2020 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.telephony.ims; + +import android.Manifest; +import android.annotation.RequiresPermission; +import android.annotation.SystemApi; +import android.content.Context; +import android.os.IBinder; +import android.os.RemoteException; +import android.os.ServiceSpecificException; +import android.telephony.CarrierConfigManager; +import android.telephony.TelephonyFrameworkInitializer; +import android.telephony.ims.aidl.IImsRcsController; + +import com.android.internal.annotations.VisibleForTesting; + +/** + * Manages the creation and destruction of SipDelegates, which allow an IMS application to forward + * SIP messages for the purposes of providing a single IMS registration to the carrier's IMS network + * from multiple sources. + * @hide + */ +@SystemApi +public class SipDelegateManager { + + private final Context mContext; + private final int mSubId; + + /** + * Only visible for testing. To instantiate an instance of this class, please use + * {@link ImsManager#getSipDelegateManager(int)}. + * @hide + */ + @VisibleForTesting + public SipDelegateManager(Context context, int subId) { + mContext = context; + mSubId = subId; + } + + /** + * Determines if creating SIP delegates are supported for the subscription specified. + * <p> + * If SIP delegates are not supported on this device or the carrier associated with this + * subscription, creating a SIP delegate will always fail, as this feature is not supported. + * @return true if this device supports creating a SIP delegate and the carrier associated with + * this subscription supports single registration, false if creating SIP delegates is not + * supported. + * @throws ImsException If the remote ImsService is not available for any reason or the + * subscription associated with this instance is no longer active. See + * {@link ImsException#getCode()} for more information. + * + * @see CarrierConfigManager.Ims#KEY_IMS_SINGLE_REGISTRATION_REQUIRED_BOOL + */ + @RequiresPermission(Manifest.permission.READ_PRIVILEGED_PHONE_STATE) + public boolean isSupported() throws ImsException { + try { + IImsRcsController controller = getIImsRcsController(); + if (controller == null) { + throw new ImsException("Telephony server is down", + ImsException.CODE_ERROR_SERVICE_UNAVAILABLE); + } + return controller.isSipDelegateSupported(mSubId); + } catch (ServiceSpecificException e) { + throw new ImsException(e.getMessage(), e.errorCode); + } catch (RemoteException e) { + throw new ImsException(e.getMessage(), + ImsException.CODE_ERROR_SERVICE_UNAVAILABLE); + } + } + + private IImsRcsController getIImsRcsController() { + IBinder binder = TelephonyFrameworkInitializer + .getTelephonyServiceManager() + .getTelephonyImsServiceRegisterer() + .get(); + return IImsRcsController.Stub.asInterface(binder); + } +} diff --git a/telephony/java/android/telephony/ims/aidl/IImsRcsController.aidl b/telephony/java/android/telephony/ims/aidl/IImsRcsController.aidl index e01ea9179452..6d25a09e079f 100644 --- a/telephony/java/android/telephony/ims/aidl/IImsRcsController.aidl +++ b/telephony/java/android/telephony/ims/aidl/IImsRcsController.aidl @@ -53,6 +53,9 @@ interface IImsRcsController { void registerUcePublishStateCallback(int subId, IRcsUcePublishStateCallback c); void unregisterUcePublishStateCallback(int subId, IRcsUcePublishStateCallback c); + // SipDelegateManager + boolean isSipDelegateSupported(int subId); + // Internal commands that should not be made public void registerRcsFeatureCallback(int slotId, in IImsServiceFeatureCallback callback); void unregisterImsFeatureCallback(in IImsServiceFeatureCallback callback); diff --git a/telephony/java/android/telephony/ims/stub/SipTransportImplBase.java b/telephony/java/android/telephony/ims/stub/SipTransportImplBase.java index 17bd4b14925f..b2b2914b3739 100644 --- a/telephony/java/android/telephony/ims/stub/SipTransportImplBase.java +++ b/telephony/java/android/telephony/ims/stub/SipTransportImplBase.java @@ -17,6 +17,7 @@ package android.telephony.ims.stub; import android.annotation.NonNull; +import android.annotation.SystemApi; import android.telephony.ims.aidl.ISipTransport; import java.util.concurrent.Executor; @@ -24,9 +25,9 @@ import java.util.concurrent.Executor; /** * Manages the creation and destruction of SipDelegates in order to proxy SIP traffic to other * IMS applications in order to support IMS single registration. - * - * @hide Until there is an implementation, keep this hidden + * @hide */ +@SystemApi public class SipTransportImplBase { private final Executor mBinderExecutor; |