diff --git a/src/com/android/phone/PhoneInterfaceManager.java b/src/com/android/phone/PhoneInterfaceManager.java
index 5ec4f65..901c8b2 100644
--- a/src/com/android/phone/PhoneInterfaceManager.java
+++ b/src/com/android/phone/PhoneInterfaceManager.java
@@ -145,10 +145,10 @@
 import android.telephony.ims.feature.ImsFeature;
 import android.telephony.ims.stub.ImsConfigImplBase;
 import android.telephony.ims.stub.ImsRegistrationImplBase;
-import android.telephony.satellite.ISatelliteCapabilitiesConsumer;
 import android.telephony.satellite.ISatelliteStateListener;
 import android.telephony.satellite.PointingInfo;
 import android.telephony.satellite.SatelliteCapabilities;
+import android.telephony.satellite.SatelliteDatagram;
 import android.telephony.satellite.SatelliteManager;
 import android.text.TextUtils;
 import android.util.ArraySet;
@@ -175,7 +175,6 @@
 import com.android.internal.telephony.IBooleanConsumer;
 import com.android.internal.telephony.ICallForwardingInfoCallback;
 import com.android.internal.telephony.IImsStateCallback;
-import com.android.internal.telephony.IIntArrayConsumer;
 import com.android.internal.telephony.IIntegerConsumer;
 import com.android.internal.telephony.INumberVerificationCallback;
 import com.android.internal.telephony.ITelephony;
@@ -394,18 +393,24 @@
     private static final int EVENT_GET_MAX_CHAR_PER_SATELLITE_TEXT_MSG_DONE = 124;
     private static final int CMD_PROVISION_SATELLITE_SERVICE = 125;
     private static final int EVENT_PROVISION_SATELLITE_SERVICE_DONE = 126;
-    private static final int CMD_CANCEL_PROVISION_SATELLITE_SERVICE = 127;
-    private static final int EVENT_CANCEL_PROVISION_SATELLITE_SERVICE_DONE = 128;
-    private static final int CMD_GET_PROVISIONED_SATELLITE_FEATURES = 129;
-    private static final int EVENT_GET_PROVISIONED_SATELLITE_FEATURES_DONE = 130;
-    private static final int CMD_SET_SATELLITE_POWER = 131;
-    private static final int EVENT_SET_SATELLITE_POWER_DONE = 132;
-    private static final int CMD_IS_SATELLITE_POWER_ON = 133;
-    private static final int EVENT_IS_SATELLITE_POWER_ON_DONE = 134;
-    private static final int CMD_IS_SATELLITE_SUPPORTED = 135;
-    private static final int EVENT_IS_SATELLITE_SUPPORTED_DONE = 136;
-    private static final int CMD_GET_SATELLITE_CAPABILITIES = 137;
-    private static final int EVENT_GET_SATELLITE_CAPABILITIES_DONE = 138;
+    private static final int CMD_DEPROVISION_SATELLITE_SERVICE = 127;
+    private static final int EVENT_DEPROVISION_SATELLITE_SERVICE_DONE = 128;
+    private static final int CMD_SET_SATELLITE_ENABLED = 129;
+    private static final int EVENT_SET_SATELLITE_ENABLED_DONE = 130;
+    private static final int CMD_IS_SATELLITE_ENABLED = 131;
+    private static final int EVENT_IS_SATELLITE_ENABLED_DONE = 132;
+    private static final int CMD_IS_SATELLITE_SUPPORTED = 133;
+    private static final int EVENT_IS_SATELLITE_SUPPORTED_DONE = 134;
+    private static final int CMD_GET_SATELLITE_CAPABILITIES = 135;
+    private static final int EVENT_GET_SATELLITE_CAPABILITIES_DONE = 136;
+    private static final int CMD_POLL_PENDING_SATELLITE_DATAGRAMS = 137;
+    private static final int EVENT_POLL_PENDING_SATELLITE_DATAGRAMS_DONE = 138;
+    private static final int CMD_SEND_SATELLITE_DATAGRAM = 139;
+    private static final int EVENT_SEND_SATELLITE_DATAGRAM_DONE = 140;
+    private static final int CMD_IS_SATELLITE_COMMUNICATION_ALLOWED = 141;
+    private static final int EVENT_IS_SATELLITE_COMMUNICATION_ALLOWED_DONE = 142;
+    private static final int CMD_GET_TIME_SATELLITE_NEXT_VISIBLE = 143;
+    private static final int EVENT_GET_TIME_SATELLITE_NEXT_VISIBLE_DONE = 144;
     // Parameters of select command.
     private static final int SELECT_COMMAND = 0xA4;
     private static final int SELECT_P1 = 0x04;
@@ -436,20 +441,39 @@
     private static final int USER_ACTIVITY_NOTIFICATION_DELAY = 200;
 
     private Set<Integer> mCarrierPrivilegeTestOverrideSubIds = new ArraySet<>();
-    private ConcurrentHashMap<IBinder, SatellitePositionUpdateHandler>
-            mSatellitePositionUpdateHandlers = new ConcurrentHashMap<>();
+
     /**
      * Map key: subId, value: callback to get error code of the provision request.
      */
-    private ConcurrentHashMap<Integer, IIntegerConsumer> mSatelliteProvisionCallbacks =
+    private final ConcurrentHashMap<Integer, Consumer<Integer>> mSatelliteProvisionCallbacks =
             new ConcurrentHashMap<>();
-
+    /**
+     * Map key: subId, value: SatellitePositionUpdateHandler to notify registrants.
+     */
+    private final ConcurrentHashMap<IBinder, SatellitePositionUpdateHandler>
+            mSatellitePositionUpdateHandlers = new ConcurrentHashMap<>();
     /**
      * Map key: subId, value: SatelliteProvisionStateChangedHandler to notify registrants.
      */
-    private ConcurrentHashMap<Integer, SatelliteProvisionStateChangedHandler>
+    private final ConcurrentHashMap<Integer, SatelliteProvisionStateChangedHandler>
             mSatelliteProvisionStateChangedHandlers = new ConcurrentHashMap<>();
 
+    private Boolean mIsSatelliteSupported = null;
+    private final Object mIsSatelliteSupportedLock = new Object();
+    private final ResultReceiver mSatelliteSupportedReceiver;
+
+    /**
+     * Map key: subId, value: SatelliteStateChangeHandler to notify registrants.
+     */
+    private ConcurrentHashMap<Integer, SatelliteStateListenerHandler>
+            mSatelliteStateListenerHandlers = new ConcurrentHashMap<>();
+
+    /**
+     * Map key: subId, value: SatelliteDatagramListenerHandler to notify registrants.
+     */
+    private ConcurrentHashMap<Integer, SatelliteDatagramListenerHandler>
+            mSatelliteDatagramListenerHandlers = new ConcurrentHashMap<>();
+
     private static final String PREF_CARRIERS_ALPHATAG_PREFIX = "carrier_alphtag_";
     private static final String PREF_CARRIERS_NUMBER_PREFIX = "carrier_number_";
     private static final String PREF_CARRIERS_SUBSCRIBER_PREFIX = "carrier_subscriber_";
@@ -545,17 +569,30 @@
     }
 
     private static final class ProvisionSatelliteServiceArgument {
-        public @NonNull int[] features;
-        public @NonNull IIntegerConsumer callback;
+        public @NonNull String token;
+        public @NonNull Consumer<Integer> callback;
         public int subId;
 
-        ProvisionSatelliteServiceArgument(int[] features, IIntegerConsumer callback, int subId) {
-            this.features = features;
+        ProvisionSatelliteServiceArgument(String token, Consumer<Integer> callback, int subId) {
+            this.token = token;
             this.callback = callback;
             this.subId = subId;
         }
     }
 
+    private static final class SendSatelliteDatagramArgument {
+        public @SatelliteManager.DatagramType int datagramType;
+        public @NonNull SatelliteDatagram datagram;
+        public @NonNull Consumer<Integer> callback;
+
+        SendSatelliteDatagramArgument(@SatelliteManager.DatagramType int datagramType,
+                SatelliteDatagram datagram, Consumer<Integer> callback) {
+            this.datagramType = datagramType;
+            this.datagram = datagram;
+            this.callback = callback;
+        }
+    }
+
     private static final class SatellitePositionUpdateHandler extends Handler {
         public static final int EVENT_POSITION_UPDATE = 1;
         public static final int EVENT_MESSAGE_TRANSFER_STATE_UPDATE = 2;
@@ -584,7 +621,8 @@
                     AsyncResult ar = (AsyncResult) msg.obj;
                     int state = (int) ar.result;
                     try {
-                        mCallback.onMessageTransferStateUpdate(state);
+                        // TODO: get correct responses back from indication
+                        mCallback.onMessageTransferStateUpdate(state, 0, 0, 0);
                     } catch (RemoteException e) {
                         loge("EVENT_MESSAGE_TRANSFER_STATE_UPDATE RemoteException: " + e);
                     }
@@ -622,19 +660,17 @@
                 case EVENT_PROVISION_STATE_CHANGED: {
                     AsyncResult ar = (AsyncResult) msg.obj;
                     boolean provisioned = (boolean) ar.userObj;
-                    int[] features = (int[]) ar.result;
                     log("Received EVENT_PROVISION_STATE_CHANGED for subId=" + mSubId
-                            + ", features=" + Arrays.toString(features)
                             + ", provisioned=" + provisioned);
                     mListeners.values().forEach(listener -> {
                         try {
-                            listener.onSatelliteProvisionStateChanged(features, provisioned);
+                            listener.onSatelliteProvisionStateChanged(provisioned);
                         } catch (RemoteException e) {
                             log("EVENT_PROVISION_STATE_CHANGED RemoteException: " + e);
                         }
                     });
 
-                    setSatelliteEnabled(provisioned);
+                    setSatelliteProvisioned(provisioned);
                     /**
                      * TODO: Take bugreport if provisioned is true and user did not initiate the
                      * provision procedure for the corresponding subscription.
@@ -646,12 +682,115 @@
             }
         }
 
-        private void setSatelliteEnabled(boolean isEnabled) {
+        private void setSatelliteProvisioned(boolean isProvisioned) {
             if (mSubId != SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) {
                 SubscriptionManager.setSubscriptionProperty(
-                        mSubId, SubscriptionManager.SATELLITE_ENABLED, isEnabled ? "1" : "0");
+                        mSubId, SubscriptionManager.SATELLITE_ENABLED, isProvisioned ? "1" : "0");
             } else {
-                //TODO (b/267826133): set enabled via SatelliteController.
+                //TODO (b/267826133): set via SatelliteController.
+            }
+        }
+    }
+
+    private static final class SatelliteStateListenerHandler extends Handler {
+        public static final int EVENT_SATELLITE_MODEM_STATE_CHANGE = 1;
+        public static final int EVENT_PENDING_MESSAGE_COUNT = 2;
+
+        private ConcurrentHashMap<IBinder, ISatelliteStateListener> mListeners;
+        private final int mSubId;
+
+        SatelliteStateListenerHandler(Looper looper, int subId) {
+            super(looper);
+            mSubId = subId;
+            mListeners = new ConcurrentHashMap<>();
+        }
+
+        public void addListener(ISatelliteStateListener listener) {
+            mListeners.put(listener.asBinder(), listener);
+        }
+
+        public boolean removeListener(ISatelliteStateListener listener) {
+            return (mListeners.remove(listener.asBinder()) != null);
+        }
+
+        @Override
+        public void handleMessage(@NonNull Message msg) {
+            switch (msg.what) {
+                case EVENT_SATELLITE_MODEM_STATE_CHANGE : {
+                    AsyncResult ar = (AsyncResult) msg.obj;
+                    int state = (int) ar.result;
+                    log("Received EVENT_SATELLITE_MODEM_STATE_CHANGE for subId=" + mSubId
+                            + ", state=" + state);
+                    mListeners.values().forEach(listener -> {
+                        try {
+                            listener.onSatelliteModemStateChange(state);
+                        } catch (RemoteException e) {
+                            log("EVENT_SATELLITE_MODEM_STATE_CHANGE RemoteException: " + e);
+                        }
+                    });
+                    break;
+                }
+                case EVENT_PENDING_MESSAGE_COUNT: {
+                    AsyncResult ar = (AsyncResult) msg.obj;
+                    int count = (int) ar.result;
+                    log("Received EVENT_PENDING_MESSAGE_COUNT for subId=" + mSubId
+                            + ", count=" + count);
+                    mListeners.values().forEach(listener -> {
+                        try {
+                            listener.onPendingMessageCount(count);
+                        } catch (RemoteException e) {
+                            log("EVENT_PENDING_MESSAGE_COUNT RemoteException: " + e);
+                        }
+                    });
+                    break;
+                }
+                default:
+                    loge("SatelliteStateListenerHandler unknown event: " + msg.what);
+            }
+        }
+    }
+
+    private static final class SatelliteDatagramListenerHandler extends Handler {
+        public static final int EVENT_SATELLITE_DATAGRAMS_RECEIVED = 1;
+
+        private ConcurrentHashMap<IBinder, ISatelliteStateListener> mListeners;
+        private final int mSubId;
+
+        SatelliteDatagramListenerHandler(Looper looper, int subId) {
+            super(looper);
+            mSubId = subId;
+            mListeners = new ConcurrentHashMap<>();
+        }
+
+        public void addListener(ISatelliteStateListener listener) {
+            mListeners.put(listener.asBinder(), listener);
+        }
+
+        public boolean removeListener(ISatelliteStateListener listener) {
+            return (mListeners.remove(listener.asBinder()) != null);
+        }
+
+        @Override
+        public void handleMessage(@NonNull Message msg) {
+            switch (msg.what) {
+                case EVENT_SATELLITE_DATAGRAMS_RECEIVED : {
+                    AsyncResult ar = (AsyncResult) msg.obj;
+                    byte[][] datagrams = (byte[][]) ar.result;
+                    SatelliteDatagram[] satelliteDatagramArray =
+                            convertToSatelliteDatagramArray(datagrams);
+
+                    log("Received EVENT_SATELLITE_DATAGRAMS_RECEIVED for subId=" + mSubId);
+                    mListeners.values().forEach(listener -> {
+                        try {
+                            listener.onSatelliteDatagrams(satelliteDatagramArray);
+                        } catch (RemoteException e) {
+                            log("EVENT_SATELLITE_DATAGRAMS_RECEIVED RemoteException: " + e);
+                        }
+                    });
+                    break;
+                }
+                default:
+                    loge("SatelliteDatagramListenerHandler unknown event: " + msg.what);
             }
         }
     }
@@ -1663,13 +1802,14 @@
                     break;
                 }
 
-                case CMD_SET_ALLOWED_CARRIERS:
+                case CMD_SET_ALLOWED_CARRIERS: {
                     request = (MainThreadRequest) msg.obj;
                     CarrierRestrictionRules argument =
                             (CarrierRestrictionRules) request.argument;
                     onCompleted = obtainMessage(EVENT_SET_ALLOWED_CARRIERS_DONE, request);
                     defaultPhone.setAllowedCarriers(argument, onCompleted, request.workSource);
                     break;
+                }
 
                 case EVENT_SET_ALLOWED_CARRIERS_DONE:
                     ar = (AsyncResult) msg.obj;
@@ -1957,7 +2097,7 @@
                 case EVENT_CMD_MODEM_REBOOT_DONE:
                     handleNullReturnEvent(msg, "rebootModem");
                     break;
-                case CMD_REQUEST_ENABLE_MODEM:
+                case CMD_REQUEST_ENABLE_MODEM: {
                     request = (MainThreadRequest) msg.obj;
                     boolean enable = (boolean) request.argument;
                     onCompleted = obtainMessage(EVENT_ENABLE_MODEM_DONE, request);
@@ -1965,6 +2105,7 @@
                     PhoneConfigurationManager.getInstance()
                             .enablePhone(request.phone, enable, onCompleted);
                     break;
+                }
                 case EVENT_ENABLE_MODEM_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
@@ -2411,9 +2552,8 @@
                         phone.startSatellitePositionUpdates(onCompleted);
                     } else {
                         loge("startSatellitePositionUpdates: No phone object");
-                        request.result =
-                                SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        ((Consumer<Integer>) request.argument).accept(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
                     }
                     break;
                 }
@@ -2421,20 +2561,8 @@
                 case EVENT_START_SATELLITE_POSITION_UPDATES_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    if (ar.exception == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("startSatellitePositionUpdates CommandException: " + ar.exception);
-                        } else {
-                            loge("startSatellitePositionUpdates unknown exception:" + ar.exception);
-                        }
-                    }
-                    notifyRequester(request);
+                    int error = getSatelliteError(ar, "startSatellitePositionUpdates", false);
+                    ((Consumer<Integer>) request.argument).accept(error);
                     break;
                 }
 
@@ -2447,9 +2575,8 @@
                         phone.stopSatellitePositionUpdates(onCompleted);
                     } else {
                         loge("stopSatellitePositionUpdates: No phone object");
-                        request.result =
-                                SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        ((Consumer<Integer>) request.argument).accept(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
                     }
                     break;
                 }
@@ -2457,20 +2584,8 @@
                 case EVENT_STOP_SATELLITE_POSITION_UPDATES_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    if (ar.exception == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("stopSatellitePositionUpdates CommandException: " + ar.exception);
-                        } else {
-                            loge("stopSatellitePositionUpdates unknown exception:" + ar.exception);
-                        }
-                    }
-                    notifyRequester(request);
+                    int error = getSatelliteError(ar, "stopSatellitePositionUpdates", false);
+                    ((Consumer<Integer>) request.argument).accept(error);
                     break;
                 }
 
@@ -2483,9 +2598,8 @@
                         phone.getMaxCharactersPerSatelliteTextMessage(onCompleted);
                     } else {
                         loge("getMaxCharactersPerSatelliteTextMessage: No phone object");
-                        request.result = SatelliteManager
-                                .SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
                     }
                     break;
                 }
@@ -2493,46 +2607,31 @@
                 case EVENT_GET_MAX_CHAR_PER_SATELLITE_TEXT_MSG_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    Consumer<Integer> callback = (Consumer<Integer>) request.argument;
-                    if (ar.exception != null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("getMaxCharactersPerSatelliteTextMessage: "
-                                    + "CommandException: " + ar.exception);
-                        } else {
-                            loge("getMaxCharactersPerSatelliteTextMessage: "
-                                    + "unknown exception:" + ar.exception);
-                        }
-                    } else if (ar.result == null) {
-                        request.result = SatelliteManager
-                                .SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        loge("getMaxCharactersPerSatelliteTextMessage: result is null");
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
+                    int error =
+                            getSatelliteError(ar, "getMaxCharactersPerSatelliteTextMessage", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
                         int maxCharLimit = ((int[]) ar.result)[0];
                         if (DBG) log("getMaxCharactersPerSatelliteTextMessage: " + maxCharLimit);
-                        callback.accept(maxCharLimit);
+                        bundle.putInt(SatelliteManager.KEY_MAX_CHARACTERS_PER_SATELLITE_TEXT,
+                                maxCharLimit);
                     }
-                    notifyRequester(request);
+                    ((ResultReceiver) request.argument).send(error, bundle);
                     break;
                 }
 
                 case CMD_PROVISION_SATELLITE_SERVICE: {
                     request = (MainThreadRequest) msg.obj;
-                    onCompleted =
-                            obtainMessage(EVENT_PROVISION_SATELLITE_SERVICE_DONE, request);
+                    onCompleted = obtainMessage(EVENT_PROVISION_SATELLITE_SERVICE_DONE, request);
                     Phone phone = getPhoneFromRequest(request);
+                    ProvisionSatelliteServiceArgument argument =
+                            (ProvisionSatelliteServiceArgument) request.argument;
                     if (phone != null) {
-                        handleCmdProvisionSatelliteService(
-                                (ProvisionSatelliteServiceArgument) request.argument,
-                                phone, onCompleted);
+                        handleCmdProvisionSatelliteService(argument, phone, onCompleted);
                     } else {
                         loge("provisionSatelliteService: No phone object");
-                        request.result =
-                                SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+                        argument.callback.accept(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
                         notifyRequester(request);
                     }
                     break;
@@ -2541,187 +2640,94 @@
                 case EVENT_PROVISION_SATELLITE_SERVICE_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    if (ar.exception == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("provisionSatelliteService CommandException: " + ar.exception);
-                        } else {
-                            loge("provisionSatelliteService unknown exception:" + ar.exception);
-                        }
-                    }
-                    handleEventProvisionSatelliteServiceDone(request);
+                    int errorCode = getSatelliteError(ar, "provisionSatelliteService", false);
+                    handleEventProvisionSatelliteServiceDone(
+                            (ProvisionSatelliteServiceArgument) request.argument, errorCode);
                     notifyRequester(request);
                     break;
                 }
 
-                case CMD_CANCEL_PROVISION_SATELLITE_SERVICE: {
+                case CMD_DEPROVISION_SATELLITE_SERVICE: {
                     request = (MainThreadRequest) msg.obj;
-                    onCompleted =
-                            obtainMessage(EVENT_CANCEL_PROVISION_SATELLITE_SERVICE_DONE, request);
-                    handleCmdCancelProvisionSatelliteService((int) request.argument, onCompleted);
-                    break;
-                }
-
-                case EVENT_CANCEL_PROVISION_SATELLITE_SERVICE_DONE: {
-                    ar = (AsyncResult) msg.obj;
-                    request = (MainThreadRequest) ar.userObj;
-
-                    if (ar.exception == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                        log("cancelProvisionSatelliteService succeeded for subId="
-                                + (int) request.argument);
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("cancelProvisionSatelliteService CommandException: "
-                                    + ar.exception + ", error code:" + request.result);
-                        } else {
-                            loge("cancelProvisionSatelliteService unknown exception:"
-                                    + ar.exception);
-                        }
-                    }
-                    notifyRequester(request);
-                    break;
-                }
-
-                case CMD_GET_PROVISIONED_SATELLITE_FEATURES: {
-                    request = (MainThreadRequest) msg.obj;
-                    onCompleted = obtainMessage(EVENT_GET_PROVISIONED_SATELLITE_FEATURES_DONE,
-                            request);
+                    onCompleted = obtainMessage(EVENT_DEPROVISION_SATELLITE_SERVICE_DONE, request);
                     Phone phone = getPhoneFromRequest(request);
+                    ProvisionSatelliteServiceArgument argument =
+                            (ProvisionSatelliteServiceArgument) request.argument;
                     if (phone != null) {
-                        phone.getProvisionedSatelliteFeatures(onCompleted);
+                        handleCmdDeprovisionSatelliteService(argument, phone, onCompleted);
                     } else {
-                        loge("getProvisionedSatelliteFeatures: No phone object");
-                        request.result = SatelliteManager
-                                .SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+                        loge("deprovisionSatelliteService: No phone object");
+                        if (argument.callback != null) {
+                            argument.callback.accept(
+                                    SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+                        }
                         notifyRequester(request);
                     }
                     break;
                 }
 
-                case EVENT_GET_PROVISIONED_SATELLITE_FEATURES_DONE: {
+                case EVENT_DEPROVISION_SATELLITE_SERVICE_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    if (ar.exception != null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("getProvisionedSatelliteFeatures: "
-                                    + "CommandException: " + ar.exception);
-                        } else {
-                            loge("getProvisionedSatelliteFeatures: "
-                                    + "unknown exception:" + ar.exception);
-                        }
-                    } else if (ar.result == null) {
-                        request.result = SatelliteManager
-                                .SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        loge("getProvisionedSatelliteFeatures: result is null");
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                        int[] features = ((int[]) ar.result);
-                        if (DBG) {
-                            log("getProvisionedSatelliteFeatures features:"
-                                    + Arrays.toString(features));
-                        }
-                        IIntArrayConsumer callback = (IIntArrayConsumer) request.argument;
-                        if (callback != null) {
-                            try {
-                                callback.accept(features);
-                            } catch (RemoteException ex) {
-                                log("getProvisionedSatelliteFeatures: remote callback"
-                                        + " not available");
-                            }
-                        } else {
-                            log("getProvisionedSatelliteFeatures: callback is null");
-                        }
-                    }
+                    int errorCode = getSatelliteError(ar, "deprovisionSatelliteService", false);
+                    handleEventDeprovisionSatelliteServiceDone(
+                            (ProvisionSatelliteServiceArgument) request.argument, errorCode);
                     notifyRequester(request);
                     break;
                 }
 
-                case CMD_SET_SATELLITE_POWER: {
+                case CMD_SET_SATELLITE_ENABLED: {
                     request = (MainThreadRequest) msg.obj;
-                    onCompleted = obtainMessage(EVENT_SET_SATELLITE_POWER_DONE, request);
+                    onCompleted = obtainMessage(EVENT_SET_SATELLITE_ENABLED_DONE, request);
+                    Pair<Boolean, Consumer<Integer>> argument =
+                            (Pair<Boolean, Consumer<Integer>>) request.argument;
                     Phone phone = getPhoneFromRequest(request);
                     if (phone != null) {
-                        phone.setSatellitePower(onCompleted, (boolean) request.argument);
+                        boolean enable = argument.first.booleanValue();
+                        phone.setSatellitePower(onCompleted, enable);
                     } else {
-                        loge("setSatellitePower: No phone object");
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+                        loge("setSatelliteEnabled: No phone object");
+                        argument.second.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
                         notifyRequester(request);
                     }
                     break;
                 }
 
-                case EVENT_SET_SATELLITE_POWER_DONE: {
+                case EVENT_SET_SATELLITE_ENABLED_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    if (ar.exception == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("setSatellitePower CommandException: " + ar.exception);
-                        } else {
-                            loge("setSatellitePower unknown exception:" + ar.exception);
-                        }
-                    }
-                    notifyRequester(request);
+                    Pair<Boolean, Consumer<Integer>> argument =
+                            (Pair<Boolean, Consumer<Integer>>) request.argument;
+                    int error = getSatelliteError(ar, "setSatelliteEnabled", false);
+                    argument.second.accept(error);
                     break;
                 }
 
-                case CMD_IS_SATELLITE_POWER_ON: {
+                case CMD_IS_SATELLITE_ENABLED: {
                     request = (MainThreadRequest) msg.obj;
-                    onCompleted = obtainMessage(EVENT_IS_SATELLITE_POWER_ON_DONE, request);
+                    onCompleted = obtainMessage(EVENT_IS_SATELLITE_ENABLED_DONE, request);
                     Phone phone = getPhoneFromRequest(request);
                     if (phone != null) {
                         phone.isSatellitePowerOn(onCompleted);
                     } else {
-                        loge("isSatellitePowerOn: No phone object");
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        loge("isSatelliteEnabled: No phone object");
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
                     }
                     break;
                 }
 
-                case EVENT_IS_SATELLITE_POWER_ON_DONE: {
+                case EVENT_IS_SATELLITE_ENABLED_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    Consumer<Boolean> callback = (Consumer<Boolean>) request.argument;
-                    if (ar.exception != null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("isSatellitePowerOn CommandException: " + ar.exception);
-                        } else {
-                            loge("isSatellitePowerOn unknown exception:" + ar.exception);
-                        }
-                    } else if (ar.result == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        loge("isSatellitePowerOn: result is null");
-                    } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                        boolean powerOn = ((int[]) ar.result)[0] == 1;
-                        if (DBG) log("isSatellitePowerOn: " + powerOn);
-                        callback.accept(powerOn);
+                    int error = getSatelliteError(ar, "isSatelliteEnabled", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
+                        boolean enabled = ((int[]) ar.result)[0] == 1;
+                        if (DBG) log("isSatelliteEnabled: " + enabled);
+                        bundle.putBoolean(SatelliteManager.KEY_SATELLITE_ENABLED, enabled);
                     }
-                    notifyRequester(request);
+                    ((ResultReceiver) request.argument).send(error, bundle);
                     break;
                 }
 
@@ -2733,8 +2739,8 @@
                         phone.isSatelliteSupported(onCompleted);
                     } else {
                         loge("isSatelliteSupported: No phone object");
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
                     }
                     break;
                 }
@@ -2742,27 +2748,21 @@
                 case EVENT_IS_SATELLITE_SUPPORTED_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    Consumer<Boolean> callback = (Consumer<Boolean>) request.argument;
-                    if (ar.exception != null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
-                        if (ar.exception instanceof CommandException) {
-                            CommandException.Error error =
-                                    ((CommandException) (ar.exception)).getCommandError();
-                            request.result = RILUtils.convertToSatelliteError(error);
-                            loge("isSatelliteSupported CommandException: " + ar.exception);
-                        } else {
-                            loge("isSatelliteSupported unknown exception:" + ar.exception);
+                    int error = getSatelliteError(ar, "isSatelliteSupported", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
+                        boolean supported = ((int[]) ar.result)[0] == 1;
+                        if (DBG) log("isSatelliteSupported: " + supported);
+                        bundle.putBoolean(SatelliteManager.KEY_SATELLITE_SUPPORTED, supported);
+                        synchronized (mIsSatelliteSupportedLock) {
+                            mIsSatelliteSupported = supported;
                         }
-                    } else if (ar.result == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        loge("isSatelliteSupported: result is null");
                     } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                        boolean powerOn = ((int[]) ar.result)[0] == 1;
-                        if (DBG) log("isSatelliteSupported: " + powerOn);
-                        callback.accept(powerOn);
+                        synchronized (mIsSatelliteSupportedLock) {
+                            mIsSatelliteSupported = null;
+                        }
                     }
-                    notifyRequester(request);
+                    ((ResultReceiver) request.argument).send(error, bundle);
                     break;
                 }
 
@@ -2774,8 +2774,8 @@
                         phone.getSatelliteCapabilities(onCompleted);
                     } else {
                         loge("getSatelliteCapabilities: No phone object");
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        notifyRequester(request);
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
                     }
                     break;
                 }
@@ -2783,31 +2783,155 @@
                 case EVENT_GET_SATELLITE_CAPABILITIES_DONE: {
                     ar = (AsyncResult) msg.obj;
                     request = (MainThreadRequest) ar.userObj;
-                    Consumer<SatelliteCapabilities> callback =
-                            (Consumer<SatelliteCapabilities>) request.argument;
+                    int error = getSatelliteError(ar, "getSatelliteCapabilities", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
+                        SatelliteCapabilities capabilities = (SatelliteCapabilities) ar.result;
+                        if (DBG) log("getSatelliteCapabilities: " + capabilities);
+                        bundle.putParcelable(SatelliteManager.KEY_SATELLITE_CAPABILITIES,
+                                capabilities);
+                    }
+                    ((ResultReceiver) request.argument).send(error, bundle);
+                    break;
+                }
+
+                case CMD_POLL_PENDING_SATELLITE_DATAGRAMS: {
+                    request = (MainThreadRequest) msg.obj;
+                    onCompleted = obtainMessage(EVENT_POLL_PENDING_SATELLITE_DATAGRAMS_DONE,
+                            request);
+                    Phone phone = getPhoneFromRequest(request);
+                    if (phone != null) {
+                        phone.pollPendingSatelliteDatagrams(onCompleted);
+                    } else {
+                        loge("pollPendingSatelliteDatagrams: No phone object");
+                        request.result = SatelliteManager
+                                .SATELLITE_INVALID_TELEPHONY_STATE;
+                        notifyRequester(request);
+                    }
+                    break;
+                }
+
+                case EVENT_POLL_PENDING_SATELLITE_DATAGRAMS_DONE: {
+                    ar = (AsyncResult) msg.obj;
+                    request = (MainThreadRequest) ar.userObj;
                     if (ar.exception != null) {
                         request.result = SatelliteManager.SATELLITE_SERVICE_ERROR;
                         if (ar.exception instanceof CommandException) {
                             CommandException.Error error =
                                     ((CommandException) (ar.exception)).getCommandError();
                             request.result = RILUtils.convertToSatelliteError(error);
-                            loge("getSatelliteCapabilities CommandException: " + ar.exception);
+                            loge("pollPendingSatelliteDatagrams: "
+                                    + "CommandException: " + ar.exception);
                         } else {
-                            loge("getSatelliteCapabilities unknown exception:" + ar.exception);
+                            loge("pollPendingSatelliteDatagrams: "
+                                    + "unknown exception:" + ar.exception);
                         }
                     } else if (ar.result == null) {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-                        loge("getSatelliteCapabilities: result is null");
+                        request.result = SatelliteManager
+                                .SATELLITE_INVALID_TELEPHONY_STATE;
+                        loge("pollPendingSatelliteDatagrams: result is null");
                     } else {
-                        request.result = SatelliteManager.SATELLITE_SERVICE_SUCCESS;
-                        SatelliteCapabilities capabilities = (SatelliteCapabilities) ar.result;
-                        if (DBG) log("getSatelliteCapabilities: " + capabilities);
-                        callback.accept(capabilities);
+                        request.result = SatelliteManager.SATELLITE_ERROR_NONE;
                     }
                     notifyRequester(request);
                     break;
                 }
 
+                case CMD_SEND_SATELLITE_DATAGRAM: {
+                    request = (MainThreadRequest) msg.obj;
+                    onCompleted =
+                            obtainMessage(EVENT_SEND_SATELLITE_DATAGRAM_DONE, request);
+                    Phone phone = getPhoneFromRequest(request);
+                    SendSatelliteDatagramArgument argument =
+                            (SendSatelliteDatagramArgument) request.argument;
+                    if (phone != null) {
+                        phone.sendSatelliteDatagram(onCompleted, argument.datagram);
+                    } else {
+                        loge("sendSatelliteDatagram: No phone object");
+                        argument.callback
+                                .accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+                    }
+                    break;
+                }
+
+                case EVENT_SEND_SATELLITE_DATAGRAM_DONE: {
+                    ar = (AsyncResult) msg.obj;
+                    request = (MainThreadRequest) ar.userObj;
+                    int error = getSatelliteError(ar, "sendSatelliteDatagram",
+                            false);
+                    SendSatelliteDatagramArgument argument =
+                            (SendSatelliteDatagramArgument) request.argument;
+                    argument.callback.accept(error);
+                    break;
+                }
+
+                case CMD_IS_SATELLITE_COMMUNICATION_ALLOWED: {
+                    request = (MainThreadRequest) msg.obj;
+                    onCompleted = obtainMessage(EVENT_IS_SATELLITE_COMMUNICATION_ALLOWED_DONE,
+                            request);
+                    Phone phone = getPhoneFromRequest(request);
+                    if (phone != null) {
+                        phone.isSatelliteCommunicationAllowedForCurrentLocation(onCompleted);
+                    } else {
+                        loge("isSatelliteCommunicationAllowedForCurrentLocation: No phone object");
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+                    }
+                    break;
+                }
+
+                case EVENT_IS_SATELLITE_COMMUNICATION_ALLOWED_DONE: {
+                    ar = (AsyncResult) msg.obj;
+                    request = (MainThreadRequest) ar.userObj;
+                    int error = getSatelliteError(
+                            ar, "isSatelliteCommunicationAllowedForCurrentLocation", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
+                        boolean communicationAllowed = ((int[]) ar.result)[0] == 1;
+                        if (DBG) {
+                            log("isSatelliteCommunicationAllowedForCurrentLocation: "
+                                    + communicationAllowed);
+                        }
+                        bundle.putBoolean(SatelliteManager.KEY_SATELLITE_COMMUNICATION_ALLOWED,
+                                communicationAllowed);
+                    }
+                    ((ResultReceiver) request.argument).send(error, bundle);
+                    break;
+                }
+
+                case CMD_GET_TIME_SATELLITE_NEXT_VISIBLE: {
+                    request = (MainThreadRequest) msg.obj;
+                    onCompleted = obtainMessage(EVENT_GET_TIME_SATELLITE_NEXT_VISIBLE_DONE,
+                            request);
+                    Phone phone = getPhoneFromRequest(request);
+                    if (phone != null) {
+                        phone.requestTimeForNextSatelliteVisibility(onCompleted);
+                    } else {
+                        loge("requestTimeForNextSatelliteVisibility: No phone object");
+                        ((ResultReceiver) request.argument).send(
+                                SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+                    }
+                    break;
+                }
+
+                case EVENT_GET_TIME_SATELLITE_NEXT_VISIBLE_DONE: {
+                    ar = (AsyncResult) msg.obj;
+                    request = (MainThreadRequest) ar.userObj;
+                    int error =
+                            getSatelliteError(ar, "requestTimeForNextSatelliteVisibility", true);
+                    Bundle bundle = new Bundle();
+                    if (error == SatelliteManager.SATELLITE_ERROR_NONE) {
+                        int nextVisibilityDuration = ((int[]) ar.result)[0];
+                        if (DBG) {
+                            log("requestTimeForNextSatelliteVisibility: " + nextVisibilityDuration);
+                        }
+                        bundle.putInt(SatelliteManager.KEY_SATELLITE_NEXT_VISIBILITY,
+                                nextVisibilityDuration);
+                    }
+                    ((ResultReceiver) request.argument).send(error, bundle);
+                    break;
+                }
+
                 default:
                     Log.w(LOG_TAG, "MainThreadHandler: unexpected message code: " + msg.what);
                     break;
@@ -3020,6 +3144,24 @@
         PropertyInvalidatedCache.invalidateCache(TelephonyManager.CACHE_KEY_PHONE_ACCOUNT_TO_SUBID);
         publish();
         CarrierAllowListInfo.loadInstance(mApp);
+        mSatelliteSupportedReceiver = new ResultReceiver(mMainThreadHandler) {
+            @Override
+            protected void onReceiveResult(int resultCode, Bundle resultData) {
+                if (resultCode == SatelliteManager.SATELLITE_ERROR_NONE
+                        && resultData.containsKey(SatelliteManager.KEY_SATELLITE_SUPPORTED)) {
+                    synchronized (mIsSatelliteSupportedLock) {
+                        mIsSatelliteSupported = resultData.getBoolean(
+                                SatelliteManager.KEY_SATELLITE_SUPPORTED);
+                    }
+                } else {
+                    synchronized (mIsSatelliteSupportedLock) {
+                        mIsSatelliteSupported = null;
+                    }
+                }
+            }
+        };
+        requestIsSatelliteSupported(SubscriptionManager.DEFAULT_SUBSCRIPTION_ID,
+                mSatelliteSupportedReceiver);
     }
 
     @VisibleForTesting
@@ -6041,7 +6183,7 @@
 
     private boolean isActiveSubscription(int subId) {
         if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-            return SubscriptionManagerService.getInstance().isActiveSubId(subId,
+            return getSubscriptionManagerService().isActiveSubId(subId,
                     mApp.getOpPackageName(), mApp.getFeatureId());
         }
         return mSubscriptionController.isActiveSubId(subId);
@@ -8007,7 +8149,7 @@
 
             ParcelUuid groupUuid;
             if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-                final SubscriptionInfo info = SubscriptionManagerService.getInstance()
+                final SubscriptionInfo info = getSubscriptionManagerService()
                         .getSubscriptionInfo(subId);
                 groupUuid = info.getGroupUuid();
             } else {
@@ -8024,7 +8166,7 @@
             final List<String> mergedSubscriberIds = new ArrayList<>();
             List<SubscriptionInfo> groupInfos;
             if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-                groupInfos = SubscriptionManagerService.getInstance()
+                groupInfos = getSubscriptionManagerService()
                         .getSubscriptionsInGroup(groupUuid, mApp.getOpPackageName(),
                                 mApp.getAttributionTag());
             } else {
@@ -8594,7 +8736,7 @@
         try {
             SubscriptionInfo info;
             if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-                info = SubscriptionManagerService.getInstance().getActiveSubscriptionInfo(subId,
+                info = getSubscriptionManagerService().getActiveSubscriptionInfo(subId,
                         phone.getContext().getOpPackageName(),
                         phone.getContext().getAttributionTag());
                 if (info == null) {
@@ -8661,7 +8803,7 @@
      */
     private List<SubscriptionInfo> getActiveSubscriptionInfoListPrivileged() {
         if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-            return SubscriptionManagerService.getInstance().getActiveSubscriptionInfoList(
+            return getSubscriptionManagerService().getActiveSubscriptionInfoList(
                     mApp.getOpPackageName(), mApp.getAttributionTag());
         }
         return mSubscriptionController.getActiveSubscriptionInfoList(mApp.getOpPackageName(),
@@ -8876,7 +9018,7 @@
         try {
             // isActiveSubId requires READ_PHONE_STATE, which we already check for above
             if (PhoneFactory.isSubscriptionManagerServiceEnabled()) {
-                SubscriptionInfoInternal subInfo = SubscriptionManagerService.getInstance()
+                SubscriptionInfoInternal subInfo = getSubscriptionManagerService()
                         .getSubscriptionInfoInternal(subId);
                 if (subInfo == null || !subInfo.isActive()) {
                     Rlog.d(LOG_TAG, "getServiceStateForSubscriber returning null for inactive "
@@ -12619,120 +12761,127 @@
     }
 
     /**
-     * Power on or off the satellite modem.
+     * Enable or disable the satellite modem. If the satellite modem is enabled, this will also
+     * disable the cellular modem, and if the satellite modem is disabled, this will also re-enable
+     * the cellular modem.
      *
-     * @param subId The subId to set satellite power for.
-     * @param powerOn {@code true} to power on the satellite modem and {@code false} to power off.
-     * @return The result of the operation.
+     * @param subId The subId of the subscription to set satellite enabled for.
+     * @param enable {@code true} to enable the satellite modem and {@code false} to disable.
+     * @param callback The callback to get the error code of the request.
      *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int setSatellitePower(int subId,
-            boolean powerOn) {
-        enforceSatelliteCommunicationPermission("setSatellitePower");
+    public void setSatelliteEnabled(int subId, boolean enable, @NonNull IIntegerConsumer callback) {
+        enforceSatelliteCommunicationPermission("setSatelliteEnabled");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(callback::accept);
+        if (!isSatelliteSupported()) {
+            result.accept(SatelliteManager.SATELLITE_NOT_SUPPORTED);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED);
+            return;
         }
 
-        Phone phone = getPhoneOrDefault(validSubId, "setSatellitePower");
+        Phone phone = getPhoneOrDefault(validSubId, "setSatelliteEnabled");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            return;
         }
 
-        int result = (int) sendRequest(CMD_SET_SATELLITE_POWER, powerOn, subId);
-        if (DBG) log("setSatellitePower result: " + result);
-        return result;
+        Pair<Boolean, Consumer<Integer>> arg = new Pair<>(enable, result);
+        sendRequestAsync(CMD_SET_SATELLITE_ENABLED, arg, phone, null);
     }
 
     /**
-     * Check whether the satellite modem is powered on.
+     * Request to get whether the satellite modem is enabled.
      *
-     * @param subId The subId to check satellite power for.
-     * @param callback The callback that will be used to send the result if the operation is
-     *                 successful. Returns {@code true} if the satellite modem is powered on and
-     *                 {@code false} otherwise.
-     * @return The result of the operation.
+     * @param subId The subId of the subscription to check whether satellite is enabled for.
+     * @param result The result receiver that returns whether the satellite modem is enabled
+     *               if the request is successful or an error code if the request failed.
      *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int isSatellitePowerOn(int subId,
-            @NonNull IBooleanConsumer callback) {
-        enforceSatelliteCommunicationPermission("isSatellitePowerOn");
+    public void requestIsSatelliteEnabled(int subId, @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission("requestIsSatelliteEnabled");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.send(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED, null);
+            return;
         }
 
-        Phone phone = getPhoneOrDefault(validSubId, "isSatellitePowerOn");
+        Phone phone = getPhoneOrDefault(validSubId, "requestIsSatelliteEnabled");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
         }
 
-        Consumer<Boolean> argument = FunctionalUtils.ignoreRemoteException(callback::accept);
-        int result = (int) sendRequest(CMD_IS_SATELLITE_POWER_ON, argument, subId);
-        if (DBG) log("isSatellitePowerOn result: " + result);
-        return result;
+        sendRequest(CMD_IS_SATELLITE_ENABLED, result, subId);
     }
 
     /**
-     * Check whether the satellite service is supported on the device.
+     * Request to get whether the satellite service is supported on the device.
      *
-     * @param subId The subId to check satellite service support for.
-     * @param callback The callback that will be used to send the result if the operation is
-     *                 successful. Returns {@code true} if the satellite service is supported on
-     *                 the device and {@code false} otherwise.
-     * @return The result of the operation.
-     *
-     * @throws SecurityException if the caller doesn't have the required permission.
+     * @param subId The subId of the subscription to check satellite service support for.
+     * @param result The result receiver that returns whether the satellite service is supported on
+     *               the device if the request is successful or an error code if the request failed.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int isSatelliteSupported(int subId,
-            @NonNull IBooleanConsumer callback) {
-        enforceSatelliteCommunicationPermission("isSatelliteSupported");
-
-        final int validSubId = getValidSatelliteSubId(subId);
-        Phone phone = getPhoneOrDefault(validSubId, "isSatelliteSupported");
-        if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+    public void requestIsSatelliteSupported(int subId, @NonNull ResultReceiver result) {
+        synchronized (mIsSatelliteSupportedLock) {
+            if (mIsSatelliteSupported != null) {
+                /* We have already successfully queried the satellite modem. */
+                Bundle bundle = new Bundle();
+                bundle.putBoolean(SatelliteManager.KEY_SATELLITE_SUPPORTED, mIsSatelliteSupported);
+                result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, bundle);
+                return;
+            }
         }
 
-        Consumer<Boolean> argument = FunctionalUtils.ignoreRemoteException(callback::accept);
-        int result = (int) sendRequest(CMD_IS_SATELLITE_SUPPORTED, argument, subId);
-        if (DBG) log("isSatelliteSupported result: " + result);
-        return result;
+        final int validSubId = getValidSatelliteSubId(subId);
+        Phone phone = getPhoneOrDefault(validSubId, "requestIsSatelliteSupported");
+        if (phone == null) {
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
+        }
+
+        sendRequestAsync(CMD_IS_SATELLITE_SUPPORTED, result, phone, null);
     }
 
     /**
-     * Get the {@link SatelliteCapabilities} with all capabilities of the satellite service.
+     * Request to get the {@link SatelliteCapabilities} of the satellite service.
      *
-     * @param subId The subId to get the satellite capabilities for.
-     * @param callback The callback that will be used to send the {@link SatelliteCapabilities}
-     *                 if the operation is successful.
-     * @return The result of the operation.
+     * @param subId The subId of the subscription to get the satellite capabilities for.
+     * @param result The result receiver that returns the {@link SatelliteCapabilities}
+     *               if the request is successful or an error code if the request failed.
      *
      * @throws SecurityException if the caller doesn't have required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int getSatelliteCapabilities(int subId,
-            @NonNull ISatelliteCapabilitiesConsumer callback) {
-        enforceSatelliteCommunicationPermission("getSatelliteCapabilities");
-
-        final int validSubId = getValidSatelliteSubId(subId);
-        Phone phone = getPhoneOrDefault(validSubId, "getSatelliteCapabilities");
-        if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+    public void requestSatelliteCapabilities(int subId, @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission("requestSatelliteCapabilities");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
         }
 
-        Consumer<SatelliteCapabilities> argument =
-                FunctionalUtils.ignoreRemoteException(callback::accept);
-        int result = (int) sendRequest(CMD_GET_SATELLITE_CAPABILITIES, argument, subId);
-        if (DBG) log("getSatelliteCapabilities result: " + result);
-        return result;
+        final int validSubId = getValidSatelliteSubId(subId);
+        Phone phone = getPhoneOrDefault(validSubId, "requestSatelliteCapabilities");
+        if (phone == null) {
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
+        }
+
+        sendRequestAsync(CMD_GET_SATELLITE_CAPABILITIES, result, phone, null);
     }
 
     /**
@@ -12740,31 +12889,41 @@
      * This can be called by the pointing UI when the user starts pointing to the satellite.
      * Modem should continue to report the pointing input as the device or satellite moves.
      *
-     * @param subId The subId to start satellite position updates for.
+     * @param subId The subId of the subscription to start satellite position updates for.
+     * @param errorCallback The callback to get the error code of the request.
      * @param callback The callback to notify of changes in satellite position.
-     * @return The result of the operation.
      *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int startSatellitePositionUpdates(int subId,
+    public void startSatellitePositionUpdates(int subId, @NonNull IIntegerConsumer errorCallback,
             @NonNull ISatelliteStateListener callback) {
         enforceSatelliteCommunicationPermission("startSatellitePositionUpdates");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(errorCallback::accept);
+        if (!isSatelliteSupported()) {
+            result.accept(SatelliteManager.SATELLITE_NOT_SUPPORTED);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED);
+            return;
         }
 
         Phone phone = getPhoneOrDefault(validSubId, "startSatellitePositionUpdates");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            return;
         }
 
         if (mSatellitePositionUpdateHandlers.containsKey(callback.asBinder())) {
-            log("startSatellitePositionUpdates: callback already registered: "
-                    + callback.asBinder());
-            return SatelliteManager.SATELLITE_SERVICE_CALLBACK_ALREADY_REGISTERED;
+            if (DBG) {
+                log("startSatellitePositionUpdates: callback already registered: "
+                        + callback.asBinder());
+            }
+            result.accept(SatelliteManager.SATELLITE_ERROR_NONE);
+            return;
         }
 
         SatellitePositionUpdateHandler handler =
@@ -12775,42 +12934,48 @@
                 SatellitePositionUpdateHandler.EVENT_MESSAGE_TRANSFER_STATE_UPDATE, null);
         mSatellitePositionUpdateHandlers.put(callback.asBinder(), handler);
 
-        int result = (int) sendRequest(CMD_START_SATELLITE_POSITION_UPDATES, null, validSubId);
-        if (DBG) log("startSatellitePositionUpdates result: " + result);
-        return result;
+        sendRequestAsync(CMD_START_SATELLITE_POSITION_UPDATES, result, phone, null);
     }
 
     /**
      * Stop receiving satellite position updates.
      * This can be called by the pointing UI when the user stops pointing to the satellite.
      *
-     * @param subId The subId to stop satellite position updates for.
-     * @param callback The callback that was passed in {@link
-     *                   #startSatellitePositionUpdates(int, ISatelliteStateListener)}
-     * @return The result of the operation.
+     * @param subId The subId of the subscription to stop satellite position updates for.
+     * @param errorCallback The callback to get the error code of the request.
+     * @param callback The callback that was passed to {@link
+     * #startSatellitePositionUpdates(int, IIntegerConsumer, ISatelliteStateListener)}
      *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult public int stopSatellitePositionUpdates(int subId,
+    public void stopSatellitePositionUpdates(int subId, @NonNull IIntegerConsumer errorCallback,
             @NonNull ISatelliteStateListener callback) {
         enforceSatelliteCommunicationPermission("stopSatellitePositionUpdates");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(errorCallback::accept);
+        if (!isSatelliteSupported()) {
+            result.accept(SatelliteManager.SATELLITE_NOT_SUPPORTED);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED);
+            return;
         }
 
         Phone phone = getPhoneOrDefault(validSubId, "stopSatellitePositionUpdates");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            return;
         }
 
         SatellitePositionUpdateHandler handler =
                 mSatellitePositionUpdateHandlers.remove(callback.asBinder());
         if (handler == null) {
-            loge("stopSatellitePositionUpdates: No SatellitePositionArgument");
-            return SatelliteManager.SATELLITE_SERVICE_CALLBACK_NOT_REGISTERED;
+            loge("stopSatellitePositionUpdates: No SatellitePositionUpdateHandler");
+            result.accept(SatelliteManager.SATELLITE_INVALID_ARGUMENTS);
+            return;
         } else {
             phone.unregisterForSatellitePointingInfoChanged(handler);
             phone.unregisterForSatelliteMessagesTransferComplete(handler);
@@ -12818,42 +12983,45 @@
 
         if (!mSatellitePositionUpdateHandlers.isEmpty()) {
             log("stopSatellitePositionUpdates: other listeners still exist.");
-            return SatelliteManager.SATELLITE_SERVICE_SUCCESS;
+            result.accept(SatelliteManager.SATELLITE_ERROR_NONE);
+            return;
         }
 
-        int result = (int) sendRequest(CMD_STOP_SATELLITE_POSITION_UPDATES, null, validSubId);
-        if (DBG) log("stopSatellitePositionUpdates result: " + result);
-        return result;
+        sendRequestAsync(CMD_STOP_SATELLITE_POSITION_UPDATES, result, phone, null);
     }
 
     /**
-     * Get maximum number of characters per text message on satellite.
-     * @param subId - The subId of the subscription.
-     * @param callback - The callback that will be used to send maximum characters limit
-     *                 if operation is successful.
-     * @return The result of the operation.
+     * Request to get the maximum number of characters per text message on satellite.
+     *
+     * @param subId The subId of the subscription to get the maximum number of characters for.
+     * @param result The result receiver that returns the maximum number of characters per text
+     *               message on satellite if the request is successful or an error code
+     *               if the request failed.
      *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    public int getMaxCharactersPerSatelliteTextMessage(int subId, IIntegerConsumer callback) {
-        enforceSatelliteCommunicationPermission("getMaxCharactersPerSatelliteTextMessage");
+    public void requestMaxCharactersPerSatelliteTextMessage(int subId,
+            @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission("requestMaxCharactersPerSatelliteTextMessage");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.send(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED, null);
+            return;
         }
 
-        Phone phone = getPhoneOrDefault(validSubId, "getMaxCharactersPerSatelliteTextMessage");
+        Phone phone = getPhoneOrDefault(validSubId, "requestMaxCharactersPerSatelliteTextMessage");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
         }
 
-        Consumer<Integer> argument = FunctionalUtils.ignoreRemoteException(callback::accept);
-        int result = (int) sendRequest(
-                CMD_GET_MAX_CHAR_PER_SATELLITE_TEXT_MSG, argument, validSubId);
-        if (DBG) log("getMaxCharPerTextMessageOnSatellite result: " + result);
-        return result;
+        sendRequestAsync(CMD_GET_MAX_CHAR_PER_SATELLITE_TEXT_MSG, result, phone, null);
     }
 
     /**
@@ -12861,191 +13029,451 @@
      * This is needed to register the subscription if the provider allows dynamic registration.
      *
      * @param subId The subId of the subscription to be provisioned.
-     * @param features List of features to be provisioned.
+     * @param token The token to be used as a unique identifier for provisioning with satellite
+     *              gateway.
      * @param callback The callback to get the error code of the request.
-     * @return The signal transport used by the caller to cancel the provision request.
+     *
+     * @return The signal transport used by the caller to cancel the provision request,
+     *         or {@code null} if the request failed.
+     *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    public ICancellationSignal provisionSatelliteService(int subId, int[] features,
-            IIntegerConsumer callback) {
+    @Nullable public ICancellationSignal provisionSatelliteService(int subId,
+            @NonNull String token, @NonNull IIntegerConsumer callback) {
         enforceSatelliteCommunicationPermission("provisionSatelliteService");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(callback::accept);
+        if (!isSatelliteSupported()) {
+            result.accept(SatelliteManager.SATELLITE_NOT_SUPPORTED);
+            return null;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        String callbackRemoteExErrorMessage = "provisionSatelliteService: callback not available.";
         Phone phone = getPhoneOrDefault(validSubId, "provisionSatelliteService");
         if (phone == null) {
-            sendResponse(callback, SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE,
-                    callbackRemoteExErrorMessage);
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
             return null;
         }
 
         if (mSatelliteProvisionCallbacks.containsKey(validSubId)) {
-            sendResponse(callback, SatelliteManager.SATELLITE_SERVICE_PROVISION_IN_PROGRESS,
-                    callbackRemoteExErrorMessage);
+            result.accept(SatelliteManager.SATELLITE_SERVICE_PROVISION_IN_PROGRESS);
             return null;
         }
 
-        if (isSatelliteEnabled(validSubId)) {
-            sendResponse(callback, SatelliteManager.SATELLITE_SERVICE_ALREADY_PROVISIONED,
-                    callbackRemoteExErrorMessage);
+        if (isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_ERROR_NONE);
             return null;
         }
 
         sendRequestAsync(CMD_PROVISION_SATELLITE_SERVICE,
-                new ProvisionSatelliteServiceArgument(features, callback, validSubId), phone, null);
+                new ProvisionSatelliteServiceArgument(token, result, validSubId), phone, null);
 
         ICancellationSignal cancelTransport = CancellationSignal.createTransport();
-        CancellationSignal.fromTransport(cancelTransport)
-                .setOnCancelListener(() -> {
-                    sendRequestAsync(CMD_CANCEL_PROVISION_SATELLITE_SERVICE, validSubId);
-                });
+        CancellationSignal.fromTransport(cancelTransport).setOnCancelListener(() -> {
+            sendRequestAsync(CMD_DEPROVISION_SATELLITE_SERVICE,
+                    new ProvisionSatelliteServiceArgument(token, null, validSubId),
+                    phone, null);
+        });
         return cancelTransport;
     }
 
     /**
+     * Unregister the device/subscription with the satellite provider.
+     * This is needed if the provider allows dynamic registration. Once deprovisioned,
+     * {@link SatelliteCallback.SatelliteProvisionStateListener#onSatelliteProvisionStateChanged}
+     * should report as deprovisioned.
+     *
+     * @param subId The subId of the subscription to be deprovisioned.
+     * @param token The token of the device/subscription to be deprovisioned.
+     * @param callback The callback to get the error code of the request.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    public void deprovisionSatelliteService(int subId,
+            @NonNull String token, @NonNull IIntegerConsumer callback) {
+        enforceSatelliteCommunicationPermission("deprovisionSatelliteService");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(callback::accept);
+        if (!isSatelliteSupported()) {
+            result.accept(SatelliteManager.SATELLITE_NOT_SUPPORTED);
+            return;
+        }
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_ERROR_NONE);
+            return;
+        }
+
+        Phone phone = getPhoneOrDefault(validSubId, "deprovisionSatelliteService");
+        if (phone == null) {
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            return;
+        }
+
+        sendRequestAsync(CMD_DEPROVISION_SATELLITE_SERVICE,
+                new ProvisionSatelliteServiceArgument(token, result, validSubId), phone, null);
+    }
+
+    /**
      * Register for the satellite provision state change.
      *
-     * @param subId The subId of the subscription associated with the satellite service.
+     * @param subId The subId of the subscription to register for provision state changes.
      * @param callback The callback to handle the satellite provision state changed event.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult
-    public int registerForSatelliteProvisionStateChanged(
-            int subId, ISatelliteStateListener callback) {
-        //enforceSatelliteCommunicationPermission("registerForSatelliteProvisionStateChanged");
-
-        final int validSubId = getValidSatelliteSubId(subId);
-        Phone phone = getPhoneOrDefault(
-                validSubId, "registerForSatelliteProvisionStateChanged");
-        if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
-        }
-
-        SatelliteProvisionStateChangedHandler satelliteProvisionStateChangedHandler =
-                mSatelliteProvisionStateChangedHandlers.get(validSubId);
-        if (satelliteProvisionStateChangedHandler == null) {
-            satelliteProvisionStateChangedHandler =
-                    new SatelliteProvisionStateChangedHandler(
-                            Looper.getMainLooper(), validSubId);
-            phone.registerForSatelliteProvisionStateChanged(
-                    satelliteProvisionStateChangedHandler,
-                    SatelliteProvisionStateChangedHandler.EVENT_PROVISION_STATE_CHANGED, null);
-        }
-
-        if (callback != null) {
-            satelliteProvisionStateChangedHandler.addListener(callback);
-        }
-        mSatelliteProvisionStateChangedHandlers.put(
-                validSubId, satelliteProvisionStateChangedHandler);
-        return SatelliteManager.SATELLITE_SERVICE_SUCCESS;
+    @SatelliteManager.SatelliteError public int registerForSatelliteProvisionStateChanged(int subId,
+            @NonNull ISatelliteStateListener callback) {
+        enforceSatelliteCommunicationPermission("registerForSatelliteProvisionStateChanged");
+        return registerForSatelliteProvisionStateChangedInternal(subId, callback);
     }
 
     /**
      * Unregister for the satellite provision state change.
      *
-     * @param subId The subId of the subscription associated with the satellite service.
-     * @param callback The callback that was passed to
-     * {@link #registerForSatelliteProvisionStateChanged(int, ISatelliteStateListener)}
+     * @param subId The subId of the subscription to unregister for provision state changes.
+     * @param errorCallback The callback to get the error code of the request.
+     * @param callback The callback that was passed to {@link
+     *                 #registerForSatelliteProvisionStateChanged(int, ISatelliteStateListener)}.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult
-    public int unregisterForSatelliteProvisionStateChanged(
-            int subId, ISatelliteStateListener callback) {
+    @SatelliteManager.SatelliteError public int unregisterForSatelliteProvisionStateChanged(
+            int subId, @NonNull ISatelliteStateListener callback) {
         enforceSatelliteCommunicationPermission("unregisterForSatelliteProvisionStateChanged");
+        if (!isSatelliteSupported()) {
+            return SatelliteManager.SATELLITE_NOT_SUPPORTED;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
         SatelliteProvisionStateChangedHandler satelliteProvisionStateChangedHandler =
                 mSatelliteProvisionStateChangedHandlers.get(validSubId);
         if (satelliteProvisionStateChangedHandler != null) {
             if (satelliteProvisionStateChangedHandler.removeListener(callback)) {
-                return SatelliteManager.SATELLITE_SERVICE_SUCCESS;
+                return SatelliteManager.SATELLITE_ERROR_NONE;
             }
         }
-        return SatelliteManager.SATELLITE_SERVICE_CALLBACK_NOT_REGISTERED;
+        return SatelliteManager.SATELLITE_INVALID_ARGUMENTS;
     }
 
     /**
-     * Get the list of provisioned satellite features.
+     * Request to get whether the device is provisioned with a satellite provider.
      *
-     * @param subId The subId of the subscription associated with the satellite service.
-     * @param callback The callback to get the list of provisioned satellite features.
-     * @return The error code of the request.
+     * @param subId The subId of the subscription to get whether the device is provisioned for.
+     * @param result The result receiver that returns whether the device is provisioned with a
+     *               satellite provider if the request is successful or an error code if the
+     *               request failed.
+     *
      * @throws SecurityException if the caller doesn't have the required permission.
      */
     @Override
-    @SatelliteManager.SatelliteServiceResult
-    public int getProvisionedSatelliteFeatures(int subId, IIntArrayConsumer callback) {
-        enforceSatelliteCommunicationPermission("getProvisionedSatelliteFeatures");
+    public void requestIsSatelliteProvisioned(int subId, @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission("requestIsSatelliteProvisioned");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
+        }
 
         final int validSubId = getValidSatelliteSubId(subId);
-        if (!isSatelliteEnabled(validSubId)) {
-            return SatelliteManager.SATELLITE_SERVICE_DISABLED;
-        }
+        Bundle bundle = new Bundle();
+        bundle.putBoolean(SatelliteManager.KEY_SATELLITE_PROVISIONED,
+                isSatelliteProvisioned(validSubId));
+        result.send(SatelliteManager.SATELLITE_ERROR_NONE, bundle);
+    }
 
-        final Phone phone = getPhoneOrDefault(validSubId, "getProvisionedSatelliteFeatures");
+    /**
+     * Register for listening to satellite state changes.
+     *
+     * @param subId The subId of the subscription to register for satellite modem state changes.
+     * @param callback The callback to handle the satellite state change event.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    @SatelliteManager.SatelliteError public int registerForSatelliteModemStateChange(int subId,
+            @NonNull ISatelliteStateListener callback) {
+        enforceSatelliteCommunicationPermission("registerForSatelliteModemStateChange");
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        Phone phone = getPhoneOrDefault(
+                validSubId, "registerForSatelliteModemStateChange");
         if (phone == null) {
-            return SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE;
+            return SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE;
         }
 
-        int result = (int) sendRequest(
-                CMD_GET_PROVISIONED_SATELLITE_FEATURES, callback, validSubId);
-        if (DBG) log("getProvisionedSatelliteFeatures result: " + result);
+        SatelliteStateListenerHandler satelliteStateListenerHandler =
+                mSatelliteStateListenerHandlers.get(validSubId);
+        if (satelliteStateListenerHandler == null) {
+            satelliteStateListenerHandler = new SatelliteStateListenerHandler(
+                    Looper.getMainLooper(), validSubId);
+            phone.registerForSatelliteModemStateChange(satelliteStateListenerHandler,
+                    SatelliteStateListenerHandler.EVENT_SATELLITE_MODEM_STATE_CHANGE, null);
+            phone.registerForPendingMessageCount(satelliteStateListenerHandler,
+                    SatelliteStateListenerHandler.EVENT_PENDING_MESSAGE_COUNT, null);
+        }
+
+        satelliteStateListenerHandler.addListener(callback);
+        mSatelliteStateListenerHandlers.put(validSubId, satelliteStateListenerHandler);
+        return SatelliteManager.SATELLITE_ERROR_NONE;
+    }
+
+    /**
+     * Unregister from listening to satellite state changes.
+     *
+     * @param subId The subId of the subscription to unregister for satellite modem state changes.
+     * @param callback The callback that was passed to
+     *                 {@link #registerForSatelliteModemStateChange(int, ISatelliteStateListener)}.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    @SatelliteManager.SatelliteError public int unregisterForSatelliteModemStateChange(int subId,
+            @NonNull ISatelliteStateListener callback) {
+        enforceSatelliteCommunicationPermission("unregisterForSatelliteModemStateChange");
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        SatelliteStateListenerHandler satelliteStateListenerHandler =
+                mSatelliteStateListenerHandlers.get(validSubId);
+        if (satelliteStateListenerHandler != null) {
+            if (satelliteStateListenerHandler.removeListener(callback)) {
+                return SatelliteManager.SATELLITE_ERROR_NONE;
+            }
+        }
+        return SatelliteManager.SATELLITE_INVALID_ARGUMENTS;
+    }
+
+    /**
+     * Register to receive incoming datagrams over satellite.
+     *
+     * @param subId The subId of the subscription to register for incoming satellite datagrams.
+     * @param datagramType Type of datagram.
+     * @param callback The callback to handle incoming datagrams over satellite.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    @SatelliteManager.SatelliteError public int registerForSatelliteDatagram(int subId,
+            @SatelliteManager.DatagramType int datagramType,
+            @NonNull ISatelliteStateListener callback) {
+        enforceSatelliteCommunicationPermission("registerForSatelliteDatagram");
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        Phone phone = getPhoneOrDefault(validSubId, "registerForSatelliteDatagram");
+        if (phone == null) {
+            return SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE;
+        }
+
+        SatelliteDatagramListenerHandler satelliteDatagramListenerHandler =
+                mSatelliteDatagramListenerHandlers.get(validSubId);
+        if (satelliteDatagramListenerHandler == null) {
+            satelliteDatagramListenerHandler = new SatelliteDatagramListenerHandler(
+                    Looper.getMainLooper(), validSubId);
+            phone.registerForNewSatelliteDatagram(satelliteDatagramListenerHandler,
+                    SatelliteDatagramListenerHandler.EVENT_SATELLITE_DATAGRAMS_RECEIVED, null);
+        }
+
+        satelliteDatagramListenerHandler.addListener(callback);
+        mSatelliteDatagramListenerHandlers.put(validSubId, satelliteDatagramListenerHandler);
+        return SatelliteManager.SATELLITE_ERROR_NONE;
+    }
+
+    /**
+     * Unregister to stop receiving incoming datagrams over satellite.
+     *
+     * @param subId The subId of the subscription to unregister for incoming satellite datagrams.
+     * @param callback The callback that was passed to
+     *                 {@link #registerForSatelliteDatagram(int, int, ISatelliteStateListener)}.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    @SatelliteManager.SatelliteError public int unregisterForSatelliteDatagram(int subId,
+            @NonNull ISatelliteStateListener callback) {
+        enforceSatelliteCommunicationPermission("unregisterForSatelliteDatagram");
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        SatelliteDatagramListenerHandler satelliteDatagramListenerHandler =
+                mSatelliteDatagramListenerHandlers.get(validSubId);
+        if (satelliteDatagramListenerHandler != null) {
+            if (satelliteDatagramListenerHandler.removeListener(callback)) {
+                return SatelliteManager.SATELLITE_ERROR_NONE;
+            }
+        }
+        return SatelliteManager.SATELLITE_INVALID_ARGUMENTS;
+    }
+
+    /**
+     * Poll pending satellite datagrams over satellite.
+     *
+     * @param subId The subId of the subscription to poll pending satellite datagrams for.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override @SatelliteManager.SatelliteError public int pollPendingSatelliteDatagrams(int subId) {
+        enforceSatelliteCommunicationPermission("pollPendingSatelliteDatagrams");
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        if (!isSatelliteProvisioned(validSubId)) {
+            return SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED;
+        }
+
+        Phone phone = getPhoneOrDefault(validSubId, "pollPendingSatelliteDatagrams");
+        if (phone == null) {
+            return SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE;
+        }
+
+        int result = (int) sendRequest(CMD_POLL_PENDING_SATELLITE_DATAGRAMS, null, validSubId);
+        if (DBG) log("pollPendingSatelliteDatagrams result: " + result);
         return result;
     }
 
+    /**
+     * Send datagram over satellite.
+     *
+     * @param subId The subId of the subscription to send satellite datagrams for.
+     * @param datagramType Type of datagram.
+     * @param datagram Datagram to send over satellite.
+     * @param callback The callback to get the error code of the request.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    public void sendSatelliteDatagram(int subId, @SatelliteManager.DatagramType int datagramType,
+            SatelliteDatagram datagram, IIntegerConsumer callback) {
+        enforceSatelliteCommunicationPermission("sendSatelliteDatagram");
+        Consumer<Integer> result = FunctionalUtils.ignoreRemoteException(callback::accept);
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.accept(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED);
+            return;
+        }
+
+        Phone phone = getPhoneOrDefault(validSubId, "sendSatelliteDatagram");
+        if (phone == null) {
+            result.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            return;
+        }
+
+        // check if we need to start PointingUI.
+
+        sendRequestAsync(CMD_SEND_SATELLITE_DATAGRAM,
+                new SendSatelliteDatagramArgument(datagramType, datagram, result),
+                phone, null);
+    }
+
+    /**
+     * Request to get whether satellite communication is allowed for the current location.
+     *
+     * @param subId The subId of the subscription to check whether satellite communication is
+     *              allowed for the current location for.
+     * @param result The result receiver that returns whether satellite communication is allowed
+     *               for the current location if the request is successful or an error code
+     *               if the request failed.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    public void requestIsSatelliteCommunicationAllowedForCurrentLocation(int subId,
+            @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission(
+                "requestIsSatelliteCommunicationAllowedForCurrentLocation");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
+        }
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.send(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED, null);
+            return;
+        }
+
+        Phone phone = getPhoneOrDefault(validSubId,
+                "requestIsSatelliteCommunicationAllowedForCurrentLocation");
+        if (phone == null) {
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
+        }
+
+        sendRequest(CMD_IS_SATELLITE_COMMUNICATION_ALLOWED, result, subId);
+    }
+
+    /**
+     * Request to get the time after which the satellite will next be visible
+     *
+     * @param subId The subId to get the time after which the satellite will next be visible for.
+     * @param result The result receiver that returns the time after which the satellite will next
+     *               be visible if the request is successful or an error code if the request failed.
+     *
+     * @throws SecurityException if the caller doesn't have the required permission.
+     */
+    @Override
+    public void requestTimeForNextSatelliteVisibility(int subId, @NonNull ResultReceiver result) {
+        enforceSatelliteCommunicationPermission("requestTimeForNextSatelliteVisibility");
+        if (!isSatelliteSupported()) {
+            result.send(SatelliteManager.SATELLITE_NOT_SUPPORTED, null);
+            return;
+        }
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        if (!isSatelliteProvisioned(validSubId)) {
+            result.send(SatelliteManager.SATELLITE_SERVICE_NOT_PROVISIONED, null);
+            return;
+        }
+
+        Phone phone = getPhoneOrDefault(validSubId, "requestTimeForNextSatelliteVisibility");
+        if (phone == null) {
+            result.send(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE, null);
+            return;
+        }
+
+        sendRequestAsync(CMD_GET_TIME_SATELLITE_NEXT_VISIBLE, result, phone, null);
+    }
+
     private void handleCmdProvisionSatelliteService(@NonNull ProvisionSatelliteServiceArgument arg,
             @NonNull Phone phone, Message onCompleted) {
-        String callbackRemoteExErrorMessage =
-                "handleCmdProvisionSatelliteService: callback not available.";
-        if (arg == null) {
-            loge("handleCmdProvisionSatelliteService: arg is null");
-            return;
-        }
-        if (phone == null) {
-            loge("handleCmdProvisionSatelliteService: phone is null");
-            sendResponse(arg.callback, SatelliteManager.SATELLITE_SERVICE_INVALID_TELEPHONY_STATE,
-                    callbackRemoteExErrorMessage);
-            return;
-        }
-
         if (!mSatelliteProvisionCallbacks.containsKey(arg.subId)) {
             mSatelliteProvisionCallbacks.put(arg.subId, arg.callback);
-            phone.provisionSatelliteService(onCompleted, phone.getImei(), phone.getMsisdn(),
-                    getSatelliteImsi(arg.subId), arg.features);
+            phone.provisionSatelliteService(onCompleted, arg.token);
         } else {
-            sendResponse(arg.callback, SatelliteManager.SATELLITE_SERVICE_PROVISION_IN_PROGRESS,
-                    callbackRemoteExErrorMessage);
+            arg.callback.accept(SatelliteManager.SATELLITE_SERVICE_PROVISION_IN_PROGRESS);
         }
     }
 
-    private void handleEventProvisionSatelliteServiceDone(MainThreadRequest request) {
-        final ProvisionSatelliteServiceArgument arg =
-                (ProvisionSatelliteServiceArgument) request.argument;
-        if (arg == null) {
-            loge("handleEventProvisionSatelliteServiceDone: arg is null");
-            return;
-        }
+    private void handleEventProvisionSatelliteServiceDone(
+            @NonNull ProvisionSatelliteServiceArgument arg,
+            @SatelliteManager.SatelliteError int result) {
+        log("handleEventProvisionSatelliteServiceDone: result="
+                + result + ", subId=" + arg.subId);
 
-        IIntegerConsumer callback = mSatelliteProvisionCallbacks.remove(arg.subId);
+        Consumer<Integer> callback = mSatelliteProvisionCallbacks.remove(arg.subId);
         if (callback == null) {
             loge("handleEventProvisionSatelliteServiceDone: callback is null for subId="
                     + arg.subId);
             return;
         }
+        callback.accept(result);
 
-        int result = (int) request.result;
-        if (DBG) {
-            log("handleEventProvisionSatelliteServiceDone: result="
-                    + result + ", subId=" + arg.subId);
-        }
-        sendResponse(callback, result,
-                "handleEventProvisionSatelliteServiceDone: callback not available.");
-
-        if (result == SatelliteManager.SATELLITE_SERVICE_SUCCESS) {
-            setSatelliteEnabled(arg.subId, true);
+        if (result == SatelliteManager.SATELLITE_ERROR_NONE) {
+            setSatelliteProvisioned(arg.subId, true);
         }
 
         /**
@@ -13053,38 +13481,43 @@
          * or SatelliteController.
          * TODO (b/267826133) we need to do this for all subscriptions on the device.
          */
-        registerForSatelliteProvisionStateChanged(arg.subId, null);
+        registerForSatelliteProvisionStateChangedInternal(arg.subId, null);
     }
 
-    private void handleCmdCancelProvisionSatelliteService(int subId, Message onCompleted) {
-        final Phone phone = getPhoneOrDefault(
-                subId, "handleCmdCancelProvisionSatelliteService");
-        if (phone == null) {
+    private void handleCmdDeprovisionSatelliteService(
+            @NonNull ProvisionSatelliteServiceArgument arg, @NonNull Phone phone,
+            @NonNull Message onCompleted) {
+        if (arg == null) {
+            loge("handleCmdDeprovisionSatelliteService: arg is null");
             return;
         }
-        phone.cancelProvisionSatelliteService(onCompleted, getSatelliteImsi(subId));
+        if (phone == null) {
+            loge("handleCmdDeprovisionSatelliteService: phone is null");
+            if (arg.callback != null) {
+                arg.callback.accept(SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE);
+            }
+            return;
+        }
+        phone.deprovisionSatelliteService(onCompleted, arg.token);
     }
 
-    private void sendResponse(@NonNull IIntegerConsumer callback, int result, String message) {
-        Objects.requireNonNull(callback);
-
-        try {
-            callback.accept(result);
-        } catch (RemoteException e) {
-            Log.w(LOG_TAG, message);
+    private void handleEventDeprovisionSatelliteServiceDone(
+            @NonNull ProvisionSatelliteServiceArgument arg,
+            @SatelliteManager.SatelliteError int result) {
+        if (arg == null) {
+            loge("handleEventDeprovisionSatelliteServiceDone: arg is null");
+            return;
         }
-    }
+        log("handleEventDeprovisionSatelliteServiceDone: result="
+                + result + ", subId=" + arg.subId);
 
-    private String getSatelliteImsi(int subId) {
-        if (subId == SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) {
-            return "";
+        if (arg.callback != null) {
+            arg.callback.accept(result);
         }
 
-        if (mSubscriptionController == null) {
-            loge("getSatelliteImsi: mSubscriptionController is null");
-            return "";
+        if (result == SatelliteManager.SATELLITE_ERROR_NONE) {
+            setSatelliteProvisioned(arg.subId, false);
         }
-        return mSubscriptionController.getImsiPrivileged(subId);
     }
 
     private Phone getPhoneOrDefault(int subId, String caller) {
@@ -13101,15 +13534,15 @@
     }
 
     /**
-     * Check if satellite is enabled for a subscription.
+     * Check if satellite is provisioned for a subscription or the device.
      *
      * Note: this is the version without permission check for telephony internal use only. The
      * caller need to take care of the permission check.
      */
-    private boolean isSatelliteEnabled(int subId) {
+    private boolean isSatelliteProvisioned(int subId) {
         if (subId != SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) {
             if (mSubscriptionController == null) {
-                loge("setSatelliteEnabled mSubscriptionController is null");
+                loge("isSatelliteProvisioned mSubscriptionController is null");
                 return false;
             }
 
@@ -13126,22 +13559,22 @@
     }
 
     /**
-     * Set satellite enabled for a subscription.
+     * Set satellite provisioned for a subscription or the device.
      *
      * The permission {@link android.Manifest.permission#MODIFY_PHONE_STATE} will be enforced by
      * {@link SubscriptionController} when setting satellite enabled for an active subscription.
      * Otherwise, {@link android.Manifest.permission#SATELLITE_COMMUNICATION} will be enforced.
      */
-    private void setSatelliteEnabled(int subId, boolean isEnabled) {
+    private synchronized void setSatelliteProvisioned(int subId, boolean isEnabled) {
         if (subId != SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) {
             if (mSubscriptionController == null) {
-                loge("setSatelliteEnabled mSubscriptionController is null");
+                loge("setSatelliteProvisioned mSubscriptionController is null");
                 return;
             }
             mSubscriptionController.setSubscriptionProperty(
                     subId, SubscriptionManager.SATELLITE_ENABLED, isEnabled ? "1" : "0");
         } else {
-            //TODO (b/267826133): enable via SatelliteController
+            //TODO (b/267826133): set via SatelliteController
         }
     }
 
@@ -13166,6 +13599,96 @@
     }
 
     /**
+     * If we have not successfully queried the satellite modem for its satellite service support,
+     * we will retry the query one more time. Otherwise, we will return the queried result.
+     */
+    private boolean isSatelliteSupported() {
+        synchronized (mIsSatelliteSupportedLock) {
+            if (mIsSatelliteSupported != null) {
+                /* We have already successfully queried the satellite modem. */
+                return mIsSatelliteSupported;
+            }
+        }
+        /**
+         * We have not successfully checked whether the modem supports satellite service.
+         * Thus, we need to retry it now.
+         */
+        requestIsSatelliteSupported(SubscriptionManager.DEFAULT_SUBSCRIPTION_ID,
+                mSatelliteSupportedReceiver);
+        return false;
+    }
+
+    /**
+     * Get the {@link SatelliteManager.SatelliteError} from the provided result.
+     *
+     * @param ar AsyncResult used to determine the error code.
+     * @param caller The satellite request.
+     * @param checkResult Whether to check if the result exists.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} error code from the request.
+     */
+    @SatelliteManager.SatelliteError private int getSatelliteError(@NonNull AsyncResult ar,
+            @NonNull String caller, boolean checkResult) {
+        int errorCode;
+        if (ar.exception == null) {
+            errorCode = SatelliteManager.SATELLITE_ERROR_NONE;
+            if (checkResult && ar.result == null) {
+                loge(caller + ": result is null");
+                errorCode = SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE;
+            }
+        } else {
+            errorCode = SatelliteManager.SATELLITE_ERROR;
+            if (ar.exception instanceof CommandException) {
+                CommandException.Error error =
+                        ((CommandException) (ar.exception)).getCommandError();
+                errorCode = RILUtils.convertToSatelliteError(error);
+                loge(caller + " CommandException: " + ar.exception);
+            } else {
+                loge(caller + " unknown exception: " + ar.exception);
+            }
+        }
+        log(caller + " error: " + errorCode);
+        return errorCode;
+    }
+
+    /**
+     * Register for the satellite provision state change.
+     *
+     * @param subId The subId of the subscription associated with the satellite service.
+     * @param callback The callback to handle the satellite provision state changed event.
+     *
+     * @return The {@link SatelliteManager.SatelliteError} result of the operation.
+     */
+    @SatelliteManager.SatelliteError private int registerForSatelliteProvisionStateChangedInternal(
+            int subId, @Nullable ISatelliteStateListener callback) {
+        if (!isSatelliteSupported()) {
+            return SatelliteManager.SATELLITE_NOT_SUPPORTED;
+        }
+
+        final int validSubId = getValidSatelliteSubId(subId);
+        Phone phone = getPhoneOrDefault(validSubId, "registerForSatelliteProvisionStateChanged");
+        if (phone == null) {
+            return SatelliteManager.SATELLITE_INVALID_TELEPHONY_STATE;
+        }
+
+        SatelliteProvisionStateChangedHandler satelliteProvisionStateChangedHandler =
+                mSatelliteProvisionStateChangedHandlers.get(validSubId);
+        if (satelliteProvisionStateChangedHandler == null) {
+            satelliteProvisionStateChangedHandler = new SatelliteProvisionStateChangedHandler(
+                    Looper.getMainLooper(), validSubId);
+            phone.registerForSatelliteProvisionStateChanged(satelliteProvisionStateChangedHandler,
+                    SatelliteProvisionStateChangedHandler.EVENT_PROVISION_STATE_CHANGED, null);
+        }
+
+        if (callback != null) {
+            satelliteProvisionStateChangedHandler.addListener(callback);
+        }
+        mSatelliteProvisionStateChangedHandlers.put(
+                validSubId, satelliteProvisionStateChangedHandler);
+        return SatelliteManager.SATELLITE_ERROR_NONE;
+    }
+
+    /**
      * Check whether the caller (or self, if not processing an IPC) can read device identifiers.
      *
      * <p>This method behaves in one of the following ways:
@@ -13190,6 +13713,13 @@
     }
 
     /**
+     * @return The subscription manager service instance.
+     */
+    public SubscriptionManagerService getSubscriptionManagerService() {
+        return SubscriptionManagerService.getInstance();
+    }
+
+    /**
      * Class binds the consumer[callback] and carrierId.
      */
     private static class CallerCallbackInfo {
@@ -13209,4 +13739,14 @@
             return mCarrierId;
         }
     }
-}
\ No newline at end of file
+
+    private static SatelliteDatagram[] convertToSatelliteDatagramArray(byte[][] datagrams) {
+        // Convert 2D byte array into SatelliteDatagramArray.
+        SatelliteDatagram[] satelliteDatagramArray =
+                new SatelliteDatagram[datagrams.length];
+        for (int i = 0; i < datagrams.length; i++) {
+            satelliteDatagramArray[i] = new SatelliteDatagram(datagrams[i]);
+        }
+        return satelliteDatagramArray;
+    }
+}
diff --git a/src/com/android/services/telephony/TelephonyConnectionService.java b/src/com/android/services/telephony/TelephonyConnectionService.java
index 519655e..2c43c7f 100644
--- a/src/com/android/services/telephony/TelephonyConnectionService.java
+++ b/src/com/android/services/telephony/TelephonyConnectionService.java
@@ -593,38 +593,36 @@
                     new DomainSelectionConnection.DomainSelectionConnectionCallback() {
         @Override
         public void onSelectionTerminated(@DisconnectCauses int cause) {
-            if (mEmergencyCallDomainSelectionConnection != null) {
+            mDomainSelectionMainExecutor.execute(() -> {
                 Log.i(this, "onSelectionTerminated cause=" + cause);
+                if (mEmergencyCallDomainSelectionConnection == null) {
+                    Log.i(this, "onSelectionTerminated no DomainSelectionConnection");
+                    return;
+                }
 
                 // Cross stack redial
                 if (cause == android.telephony.DisconnectCause.EMERGENCY_TEMP_FAILURE
                         || cause == android.telephony.DisconnectCause.EMERGENCY_PERM_FAILURE) {
                     if (mEmergencyConnection != null) {
-                        final boolean isPermanentFailure =
+                        boolean isPermanentFailure =
                                 cause == android.telephony.DisconnectCause.EMERGENCY_PERM_FAILURE;
-                        Log.i(this, "onSelectionTerminated trigger cross stack redial"
-                                + " permanent=" + isPermanentFailure);
-                        mDomainSelectionMainExecutor.execute(() -> {
-                            Log.i(this, "onSelectionTerminated execute cross stack redial"
-                                    + " permanent=" + isPermanentFailure);
-                            TelephonyConnection c = mEmergencyConnection;
-                            Phone phone = mEmergencyCallDomainSelectionConnection.getPhone();
-                            mEmergencyConnection.removeTelephonyConnectionListener(
-                                    mEmergencyConnectionListener);
-                            mEmergencyStateTracker.endCall(
-                                    mEmergencyConnection.getTelecomCallId());
-                            releaseEmergencyCallDomainSelection(true);
-                            retryOutgoingOriginalConnection(c, phone, isPermanentFailure);
-                        });
+                        Log.i(this, "onSelectionTerminated permanent=" + isPermanentFailure);
+                        TelephonyConnection c = mEmergencyConnection;
+                        Phone phone = mEmergencyCallDomainSelectionConnection.getPhone();
+                        mEmergencyConnection.removeTelephonyConnectionListener(
+                                mEmergencyConnectionListener);
+                        releaseEmergencyCallDomainSelection(true);
+                        mEmergencyStateTracker.endCall(mEmergencyCallId);
+                        mEmergencyCallId = null;
+                        retryOutgoingOriginalConnection(c, phone, isPermanentFailure);
                         return;
                     }
                 }
-                mEmergencyCallDomainSelectionConnection = null;
                 if (mEmergencyConnection != null) {
                     mEmergencyConnection.hangup(android.telephony.DisconnectCause.OUT_OF_NETWORK);
                     mEmergencyConnection = null;
                 }
-            }
+            });
         }
     };
 
@@ -2386,9 +2384,9 @@
 
         Log.i(this, "maybeReselectDomainForEmergencyCall endCall()");
         c.removeTelephonyConnectionListener(mEmergencyConnectionListener);
-        mEmergencyStateTracker.endCall(c.getTelecomCallId());
         releaseEmergencyCallDomainSelection(true);
-
+        mEmergencyStateTracker.endCall(c.getTelecomCallId());
+        mEmergencyCallId = null;
         return false;
     }
 
@@ -2410,7 +2408,7 @@
                 + ", psCause:" + reasonInfo);
 
         if (mDomainSelectionConnection != null && c.getOriginalConnection() != null) {
-            Phone phone = c.getPhone();
+            Phone phone = c.getPhone().getDefaultPhone();
             final String number = c.getAddress().getSchemeSpecificPart();
             int videoState = c.getOriginalConnection().getVideoState();
             SelectionAttributes selectionAttributes = NormalCallDomainSelectionConnection
@@ -2424,7 +2422,7 @@
                     .reselectDomain(selectionAttributes);
             if (future != null) {
                 future.thenAcceptAsync((result) -> {
-                    onNormalCallRedial(c, result, videoState);
+                    onNormalCallRedial(c, phone, result, videoState);
                 }, mDomainSelectionMainExecutor);
                 return true;
             }
@@ -2598,14 +2596,13 @@
         onEmergencyRedialOnDomain(connection, phone, result);
     }
 
-    private void onNormalCallRedial(TelephonyConnection connection,
+    private void onNormalCallRedial(TelephonyConnection connection, Phone phone,
             @NetworkRegistrationInfo.Domain int domain, int videocallState) {
 
         Log.v(LOG_TAG, "Redialing the call in domain:"
                 + DomainSelectionService.getDomainName(domain));
 
         String number = connection.getAddress().getSchemeSpecificPart();
-        Phone phone = connection.getPhone();
 
         Bundle extras = new Bundle();
         extras.putInt(PhoneConstants.EXTRA_DIAL_DOMAIN, domain);
@@ -2647,8 +2644,8 @@
         if (TextUtils.equals(mEmergencyCallId, c.getTelecomCallId())) {
             Log.i(this, "onLocalHangup " + mEmergencyCallId);
             c.removeTelephonyConnectionListener(mEmergencyConnectionListener);
-            mEmergencyStateTracker.endCall(c.getTelecomCallId());
             releaseEmergencyCallDomainSelection(true);
+            mEmergencyStateTracker.endCall(c.getTelecomCallId());
             mEmergencyCallId = null;
         }
     }
diff --git a/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelector.java b/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelector.java
index e8825be..a23d0b7 100644
--- a/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelector.java
+++ b/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelector.java
@@ -255,7 +255,7 @@
 
         if (result.getAccessNetwork() == UNKNOWN) {
             if ((mPreferredNetworkScanType == SCAN_TYPE_FULL_SERVICE_FOLLOWED_BY_LIMITED_SERVICE)
-                      || (mScanType == DomainSelectionService.SCAN_TYPE_FULL_SERVICE)) {
+                      && (mScanType == DomainSelectionService.SCAN_TYPE_FULL_SERVICE)) {
                 mScanType = DomainSelectionService.SCAN_TYPE_LIMITED_SERVICE;
                 mWwanSelectorCallback.onRequestEmergencyNetworkScan(
                         mLastPreferredNetworks, mScanType, mCancelSignal,
diff --git a/tests/src/com/android/phone/PhoneInterfaceManagerTest.java b/tests/src/com/android/phone/PhoneInterfaceManagerTest.java
index 4cc793d..e702279 100644
--- a/tests/src/com/android/phone/PhoneInterfaceManagerTest.java
+++ b/tests/src/com/android/phone/PhoneInterfaceManagerTest.java
@@ -21,7 +21,6 @@
 import static org.junit.Assert.assertThrows;
 import static org.junit.Assert.assertTrue;
 import static org.mockito.ArgumentMatchers.anyInt;
-import static org.mockito.ArgumentMatchers.anyList;
 import static org.mockito.ArgumentMatchers.anyString;
 import static org.mockito.Mockito.doNothing;
 import static org.mockito.Mockito.doReturn;
@@ -42,9 +41,10 @@
 import androidx.test.ext.junit.runners.AndroidJUnit4;
 
 import com.android.TelephonyTestBase;
+import com.android.internal.telephony.IIntegerConsumer;
 import com.android.internal.telephony.Phone;
 import com.android.internal.telephony.RILConstants;
-import com.android.internal.telephony.IIntegerConsumer;
+import com.android.internal.telephony.subscription.SubscriptionManagerService;
 
 import org.junit.Before;
 import org.junit.Test;
@@ -54,7 +54,7 @@
 import java.util.Locale;
 
 /**
- * Unit Test for CarrierConfigLoader.
+ * Unit Test for PhoneInterfaceManager.
  */
 @RunWith(AndroidJUnit4.class)
 public class PhoneInterfaceManagerTest extends TelephonyTestBase {
@@ -67,6 +67,9 @@
     @Mock
     Phone mPhone;
 
+    @Mock
+    private SubscriptionManagerService mSubscriptionManagerService;
+
     @Before
     @UiThreadTest
     public void setUp() throws Exception {
@@ -76,6 +79,9 @@
         // alive on a test devices. You must use the spy to mock behavior. Mocks stemming from the
         // passed context will remain unused.
         mPhoneInterfaceManager = spy(PhoneInterfaceManager.init(mPhoneGlobals));
+        doReturn(mSubscriptionManagerService).when(mPhoneInterfaceManager)
+                .getSubscriptionManagerService();
+        TelephonyManager.setupISubForTest(mSubscriptionManagerService);
         mSharedPreferences = mPhoneInterfaceManager.getSharedPreferences();
         mSharedPreferences.edit().remove(Phone.PREF_NULL_CIPHER_AND_INTEGRITY_ENABLED).commit();
         mIIntegerConsumer = mock(IIntegerConsumer.class);
diff --git a/tests/src/com/android/phone/euicc/EuiccUiDispatcherActivityTest.java b/tests/src/com/android/phone/euicc/EuiccUiDispatcherActivityTest.java
index 8b0ac5c..817220c 100644
--- a/tests/src/com/android/phone/euicc/EuiccUiDispatcherActivityTest.java
+++ b/tests/src/com/android/phone/euicc/EuiccUiDispatcherActivityTest.java
@@ -23,6 +23,7 @@
 import android.content.Context;
 import android.content.Intent;
 import android.content.pm.ActivityInfo;
+import android.service.euicc.EuiccService;
 import android.telephony.euicc.EuiccManager;
 
 import androidx.test.InstrumentationRegistry;
@@ -111,6 +112,24 @@
         assertEquals("bar", euiccUiIntent.getStringExtra("foo"));
     }
 
+    @Test
+    public void testTransferEmbeddedSubscriptionsAction() {
+        mIntent = new Intent(EuiccManager.ACTION_TRANSFER_EMBEDDED_SUBSCRIPTIONS);
+        Intent euiccUiIntent = mActivity.resolveEuiccUiIntent();
+        assertNotNull(euiccUiIntent);
+        assertEquals(EuiccService.ACTION_TRANSFER_EMBEDDED_SUBSCRIPTIONS,
+                euiccUiIntent.getAction());
+    }
+
+    @Test
+    public void testConvertToEmbeddedSubscriptionAction() {
+        mIntent = new Intent(EuiccManager.ACTION_CONVERT_TO_EMBEDDED_SUBSCRIPTION);
+        Intent euiccUiIntent = mActivity.resolveEuiccUiIntent();
+        assertNotNull(euiccUiIntent);
+        assertEquals(EuiccService.ACTION_CONVERT_TO_EMBEDDED_SUBSCRIPTION,
+                euiccUiIntent.getAction());
+    }
+
     class TestEuiccUiDispatcherActivity extends EuiccUiDispatcherActivity {
         public TestEuiccUiDispatcherActivity() {
             attachBaseContext(mMockContext);
diff --git a/tests/src/com/android/services/telephony/TelephonyConnectionServiceTest.java b/tests/src/com/android/services/telephony/TelephonyConnectionServiceTest.java
index 61060d9..4826d89 100644
--- a/tests/src/com/android/services/telephony/TelephonyConnectionServiceTest.java
+++ b/tests/src/com/android/services/telephony/TelephonyConnectionServiceTest.java
@@ -18,6 +18,7 @@
 
 import static android.telephony.DisconnectCause.EMERGENCY_PERM_FAILURE;
 import static android.telephony.DisconnectCause.EMERGENCY_TEMP_FAILURE;
+import static android.telephony.DisconnectCause.ERROR_UNSPECIFIED;
 import static android.telephony.DisconnectCause.NOT_DISCONNECTED;
 import static android.telephony.DomainSelectionService.SELECTOR_TYPE_CALLING;
 import static android.telephony.NetworkRegistrationInfo.DOMAIN_CS;
@@ -1952,6 +1953,40 @@
     }
 
     @Test
+    public void testOnSelectionTerminatedUnspecified() throws Exception {
+        setupForCallTest();
+
+        doReturn(mEmergencyCallDomainSelectionConnection).when(mDomainSelectionResolver)
+                .getDomainSelectionConnection(any(), anyInt(), eq(true));
+        doReturn(mPhone0).when(mEmergencyCallDomainSelectionConnection).getPhone();
+        doReturn(true).when(mTelephonyManagerProxy).isCurrentEmergencyNumber(anyString());
+
+        doReturn(true).when(mDomainSelectionResolver).isDomainSelectionSupported();
+        doReturn(mImsPhone).when(mPhone0).getImsPhone();
+
+        mTestConnectionService.onCreateOutgoingConnection(PHONE_ACCOUNT_HANDLE_1,
+                createConnectionRequest(PHONE_ACCOUNT_HANDLE_1,
+                        TEST_EMERGENCY_NUMBER, TELECOM_CALL_ID1));
+
+        ArgumentCaptor<DomainSelectionConnection.DomainSelectionConnectionCallback> callbackCaptor =
+                ArgumentCaptor.forClass(
+                        DomainSelectionConnection.DomainSelectionConnectionCallback.class);
+
+        verify(mEmergencyCallDomainSelectionConnection).createEmergencyConnection(
+                any(), callbackCaptor.capture());
+
+        DomainSelectionConnection.DomainSelectionConnectionCallback callback =
+                callbackCaptor.getValue();
+
+        assertNotNull(callback);
+
+        callback.onSelectionTerminated(ERROR_UNSPECIFIED);
+
+        verify(mEmergencyCallDomainSelectionConnection).cancelSelection();
+        verify(mEmergencyStateTracker).endCall(eq(TELECOM_CALL_ID1));
+    }
+
+    @Test
     public void testDomainSelectionLocalHangupStartEmergencyCall() throws Exception {
         setupForCallTest();
 
diff --git a/tests/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelectorTest.java b/tests/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelectorTest.java
index 7649f5a..673e586 100644
--- a/tests/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelectorTest.java
+++ b/tests/src/com/android/services/telephony/domainselection/EmergencyCallDomainSelectorTest.java
@@ -38,6 +38,8 @@
 import static android.telephony.CarrierConfigManager.ImsEmergency.KEY_EMERGENCY_VOWIFI_REQUIRES_CONDITION_INT;
 import static android.telephony.CarrierConfigManager.ImsEmergency.KEY_MAXIMUM_NUMBER_OF_EMERGENCY_TRIES_OVER_VOWIFI_INT;
 import static android.telephony.CarrierConfigManager.ImsEmergency.KEY_PREFER_IMS_EMERGENCY_WHEN_VOICE_CALLS_ON_CS_BOOL;
+import static android.telephony.CarrierConfigManager.ImsEmergency.SCAN_TYPE_FULL_SERVICE;
+import static android.telephony.CarrierConfigManager.ImsEmergency.SCAN_TYPE_FULL_SERVICE_FOLLOWED_BY_LIMITED_SERVICE;
 import static android.telephony.CarrierConfigManager.ImsEmergency.SCAN_TYPE_NO_PREFERENCE;
 import static android.telephony.CarrierConfigManager.ImsEmergency.VOWIFI_REQUIRES_NONE;
 import static android.telephony.CarrierConfigManager.ImsEmergency.VOWIFI_REQUIRES_SETTING_ENABLED;
@@ -1167,6 +1169,67 @@
     }
 
     @Test
+    public void testFullService() throws Exception {
+        PersistableBundle bundle = getDefaultPersistableBundle();
+        bundle.putInt(KEY_EMERGENCY_NETWORK_SCAN_TYPE_INT, SCAN_TYPE_FULL_SERVICE);
+        when(mCarrierConfigManager.getConfigForSubId(anyInt())).thenReturn(bundle);
+
+        mResultConsumer = null;
+        createSelector(SLOT_0_SUB_ID);
+        unsolBarringInfoChanged(true);
+
+        EmergencyRegResult regResult = getEmergencyRegResult(UNKNOWN, REGISTRATION_STATE_UNKNOWN,
+                0, false, false, 0, 0, "", "");
+        SelectionAttributes attr = getSelectionAttributes(SLOT_0, SLOT_0_SUB_ID, regResult);
+        mDomainSelector.selectDomain(attr, mTransportSelectorCallback);
+        processAllMessages();
+
+        bindImsServiceUnregistered();
+        processAllMessages();
+
+        verify(mWwanSelectorCallback, times(1)).onRequestEmergencyNetworkScan(
+                any(), eq(DomainSelectionService.SCAN_TYPE_FULL_SERVICE), any(), any());
+        assertNotNull(mResultConsumer);
+
+        mResultConsumer.accept(regResult);
+        processAllMessages();
+
+        verify(mWwanSelectorCallback, times(2)).onRequestEmergencyNetworkScan(
+                any(), eq(DomainSelectionService.SCAN_TYPE_FULL_SERVICE), any(), any());
+    }
+
+    @Test
+    public void testFullServiceThenLimtedService() throws Exception {
+        PersistableBundle bundle = getDefaultPersistableBundle();
+        bundle.putInt(KEY_EMERGENCY_NETWORK_SCAN_TYPE_INT,
+                SCAN_TYPE_FULL_SERVICE_FOLLOWED_BY_LIMITED_SERVICE);
+        when(mCarrierConfigManager.getConfigForSubId(anyInt())).thenReturn(bundle);
+
+        mResultConsumer = null;
+        createSelector(SLOT_0_SUB_ID);
+        unsolBarringInfoChanged(true);
+
+        EmergencyRegResult regResult = getEmergencyRegResult(UNKNOWN, REGISTRATION_STATE_UNKNOWN,
+                0, false, false, 0, 0, "", "");
+        SelectionAttributes attr = getSelectionAttributes(SLOT_0, SLOT_0_SUB_ID, regResult);
+        mDomainSelector.selectDomain(attr, mTransportSelectorCallback);
+        processAllMessages();
+
+        bindImsServiceUnregistered();
+        processAllMessages();
+
+        verify(mWwanSelectorCallback, times(1)).onRequestEmergencyNetworkScan(
+                any(), eq(DomainSelectionService.SCAN_TYPE_FULL_SERVICE), any(), any());
+        assertNotNull(mResultConsumer);
+
+        mResultConsumer.accept(regResult);
+        processAllMessages();
+
+        verify(mWwanSelectorCallback, times(1)).onRequestEmergencyNetworkScan(
+                any(), eq(DomainSelectionService.SCAN_TYPE_LIMITED_SERVICE), any(), any());
+    }
+
+    @Test
     public void testCsThenPsPreference() throws Exception {
         PersistableBundle bundle = getDefaultPersistableBundle();
         int[] domainPreference = new int[] {
