Add RIL requests and unsol for Satellite HAL

Bug: 260644201
Test: atest VtsHalRadioTargetTest
atest TelephonyManagerTestOnMockModem
MO/MT SMS, MMS, voice calls with live network

Change-Id: I27e1cfe9442786333b694190c123edf762d7db60
diff --git a/Android.bp b/Android.bp
index cfab18e..ea7ced9 100644
--- a/Android.bp
+++ b/Android.bp
@@ -224,6 +224,7 @@
         "android.hardware.radio.messaging-V2-java",
         "android.hardware.radio.modem-V2-java",
         "android.hardware.radio.network-V2-java",
+        "android.hardware.radio.satellite-V1-java",
         "android.hardware.radio.sim-V2-java",
         "android.hardware.radio.voice-V2-java",
         "android.hardware.thermal-V1.0-java-constants",
diff --git a/core/api/test-current.txt b/core/api/test-current.txt
index d6ce1589..f75bd3b 100644
--- a/core/api/test-current.txt
+++ b/core/api/test-current.txt
@@ -2793,6 +2793,7 @@
     field public static final int HAL_SERVICE_MESSAGING = 2; // 0x2
     field public static final int HAL_SERVICE_MODEM = 3; // 0x3
     field public static final int HAL_SERVICE_NETWORK = 4; // 0x4
+    field public static final int HAL_SERVICE_SATELLITE = 8; // 0x8
     field public static final int HAL_SERVICE_SIM = 5; // 0x5
     field public static final int HAL_SERVICE_VOICE = 6; // 0x6
     field public static final android.util.Pair HAL_VERSION_UNKNOWN;
diff --git a/telephony/java/android/telephony/TelephonyManager.java b/telephony/java/android/telephony/TelephonyManager.java
index 913ea9a..3aba579 100644
--- a/telephony/java/android/telephony/TelephonyManager.java
+++ b/telephony/java/android/telephony/TelephonyManager.java
@@ -14977,6 +14977,14 @@
     @TestApi
     public static final int HAL_SERVICE_IMS = 7;
 
+    /**
+     * HAL service type that supports the HAL APIs implementation of IRadioSatellite
+     * {@link RadioSatelliteProxy}
+     * @hide
+     */
+    @TestApi
+    public static final int HAL_SERVICE_SATELLITE = 8;
+
     /** @hide */
     @Retention(RetentionPolicy.SOURCE)
     @IntDef(prefix = {"HAL_SERVICE_"},
@@ -14989,6 +14997,7 @@
                     HAL_SERVICE_SIM,
                     HAL_SERVICE_VOICE,
                     HAL_SERVICE_IMS,
+                    HAL_SERVICE_SATELLITE
             })
     public @interface HalService {}
 
diff --git a/telephony/java/android/telephony/satellite/PointingInfo.java b/telephony/java/android/telephony/satellite/PointingInfo.java
new file mode 100644
index 0000000..d6dd57a
--- /dev/null
+++ b/telephony/java/android/telephony/satellite/PointingInfo.java
@@ -0,0 +1,144 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.telephony.satellite;
+
+import android.annotation.NonNull;
+import android.os.Parcel;
+import android.os.Parcelable;
+
+/**
+ * @hide
+ */
+public final class PointingInfo implements Parcelable {
+    /** Satellite azimuth in degrees */
+    private float mSatelliteAzimuthDegrees;
+
+    /** Satellite elevation in degrees */
+    private float mSatelliteElevationDegrees;
+
+    /** Antenna azimuth in degrees */
+    private float mAntennaAzimuthDegrees;
+
+    /**
+     * Angle of rotation about the x axis. This value represents the angle between a plane
+     * parallel to the device's screen and a plane parallel to the ground.
+     */
+    private float mAntennaPitchDegrees;
+
+    /**
+     * Angle of rotation about the y axis. This value represents the angle between a plane
+     * perpendicular to the device's screen and a plane parallel to the ground.
+     */
+    private float mAntennaRollDegrees;
+
+    /**
+     * @hide
+     */
+    public PointingInfo(float satelliteAzimuthDegress, float satelliteElevationDegress,
+            float antennaAzimuthDegrees, float antennaPitchDegrees, float antennaRollDegrees) {
+        mSatelliteAzimuthDegrees = satelliteAzimuthDegress;
+        mSatelliteElevationDegrees = satelliteElevationDegress;
+        mAntennaAzimuthDegrees = antennaAzimuthDegrees;
+        mAntennaPitchDegrees = antennaPitchDegrees;
+        mAntennaRollDegrees = antennaRollDegrees;
+    }
+
+    private PointingInfo(Parcel in) {
+        readFromParcel(in);
+    }
+
+    @Override
+    public int describeContents() {
+        return 0;
+    }
+
+    @Override
+    public void writeToParcel(@NonNull Parcel out, int flags) {
+        out.writeFloat(mSatelliteAzimuthDegrees);
+        out.writeFloat(mSatelliteElevationDegrees);
+        out.writeFloat(mAntennaAzimuthDegrees);
+        out.writeFloat(mAntennaPitchDegrees);
+        out.writeFloat(mAntennaRollDegrees);
+    }
+
+    public static final @android.annotation.NonNull Creator<PointingInfo> CREATOR =
+            new Creator<PointingInfo>() {
+                @Override
+                public PointingInfo createFromParcel(Parcel in) {
+                    return new PointingInfo(in);
+                }
+
+                @Override
+                public PointingInfo[] newArray(int size) {
+                    return new PointingInfo[size];
+                }
+            };
+
+    @NonNull
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+
+        sb.append("SatelliteAzimuthDegrees:");
+        sb.append(mSatelliteAzimuthDegrees);
+        sb.append(",");
+
+        sb.append("SatelliteElevationDegrees:");
+        sb.append(mSatelliteElevationDegrees);
+        sb.append(",");
+
+        sb.append("AntennaAzimuthDegrees:");
+        sb.append(mAntennaAzimuthDegrees);
+        sb.append(",");
+
+        sb.append("AntennaPitchDegrees:");
+        sb.append(mAntennaPitchDegrees);
+        sb.append(",");
+
+        sb.append("AntennaRollDegrees:");
+        sb.append(mAntennaRollDegrees);
+        return sb.toString();
+    }
+
+    public float getSatelliteAzimuthDegrees() {
+        return mSatelliteAzimuthDegrees;
+    }
+
+    public float getSatelliteElevationDegrees() {
+        return mSatelliteElevationDegrees;
+    }
+
+    public float getAntennaAzimuthDegrees() {
+        return mAntennaAzimuthDegrees;
+    }
+
+    public float getAntennaPitchDegrees() {
+        return mAntennaPitchDegrees;
+    }
+
+    public float getAntennaRollDegrees() {
+        return mAntennaRollDegrees;
+    }
+
+    private void readFromParcel(Parcel in) {
+        mSatelliteAzimuthDegrees = in.readFloat();
+        mSatelliteElevationDegrees = in.readFloat();
+        mAntennaAzimuthDegrees = in.readFloat();
+        mAntennaPitchDegrees = in.readFloat();
+        mAntennaRollDegrees = in.readFloat();
+    }
+}
diff --git a/telephony/java/android/telephony/satellite/SatelliteCapabilities.java b/telephony/java/android/telephony/satellite/SatelliteCapabilities.java
new file mode 100644
index 0000000..c5ae4db
--- /dev/null
+++ b/telephony/java/android/telephony/satellite/SatelliteCapabilities.java
@@ -0,0 +1,201 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.telephony.satellite;
+
+import android.annotation.NonNull;
+import android.os.Parcel;
+import android.os.Parcelable;
+
+import java.util.HashSet;
+import java.util.Set;
+
+/**
+ * @hide
+ */
+public final class SatelliteCapabilities implements Parcelable {
+    /**
+     * List of technologies supported by the satellite modem.
+     */
+    private Set<Integer> mSupportedRadioTechnologies;
+
+    /**
+     * Whether satellite mode is always on (this to indicate power impact of keeping it on is
+     * very minimal).
+     */
+    private boolean mIsAlwaysOn;
+
+    /**
+     * Whether UE needs to point to a satellite to send and receive data.
+     */
+    private boolean mNeedsPointingToSatellite;
+
+    /**
+     * List of features supported by the Satellite modem.
+     */
+    private Set<Integer> mSupportedFeatures;
+
+    /**
+     * Whether UE needs a separate SIM profile to communicate with the Satellite network.
+     */
+    private boolean mNeedsSeparateSimProfile;
+
+    /**
+     * @hide
+     */
+    public SatelliteCapabilities(Set<Integer> supportedRadioTechnologies, boolean isAlwaysOn,
+            boolean needsPointingToSatellite, Set<Integer> supportedFeatures,
+            boolean needsSeparateSimProfile) {
+        mSupportedRadioTechnologies = supportedRadioTechnologies;
+        mIsAlwaysOn = isAlwaysOn;
+        mNeedsPointingToSatellite = needsPointingToSatellite;
+        mSupportedFeatures = supportedFeatures;
+        mNeedsSeparateSimProfile = needsSeparateSimProfile;
+    }
+
+    private SatelliteCapabilities(Parcel in) {
+        readFromParcel(in);
+    }
+
+    @Override
+    public int describeContents() {
+        return 0;
+    }
+
+    @Override
+    public void writeToParcel(@NonNull Parcel out, int flags) {
+        if (mSupportedRadioTechnologies != null && !mSupportedRadioTechnologies.isEmpty()) {
+            out.writeInt(mSupportedRadioTechnologies.size());
+            for (int technology : mSupportedRadioTechnologies) {
+                out.writeInt(technology);
+            }
+        } else {
+            out.writeInt(0);
+        }
+
+        out.writeBoolean(mIsAlwaysOn);
+        out.writeBoolean(mNeedsPointingToSatellite);
+
+        if (mSupportedFeatures != null && !mSupportedFeatures.isEmpty()) {
+            out.writeInt(mSupportedFeatures.size());
+            for (int feature : mSupportedFeatures) {
+                out.writeInt(feature);
+            }
+        } else {
+            out.writeInt(0);
+        }
+
+        out.writeBoolean(mNeedsSeparateSimProfile);
+    }
+
+    public static final @android.annotation.NonNull Creator<SatelliteCapabilities> CREATOR =
+            new Creator<SatelliteCapabilities>() {
+                @Override
+                public SatelliteCapabilities createFromParcel(Parcel in) {
+                    return new SatelliteCapabilities(in);
+                }
+
+                @Override
+                public SatelliteCapabilities[] newArray(int size) {
+                    return new SatelliteCapabilities[size];
+                }
+            };
+
+    @NonNull
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+
+        sb.append("SupportedRadioTechnology:");
+        if (mSupportedRadioTechnologies != null && !mSupportedRadioTechnologies.isEmpty()) {
+            for (int technology : mSupportedRadioTechnologies) {
+                sb.append(technology);
+                sb.append(",");
+            }
+        } else {
+            sb.append("none,");
+        }
+
+        sb.append("SupportedFeatures:");
+        if (mSupportedFeatures != null && !mSupportedFeatures.isEmpty()) {
+            for (int feature : mSupportedFeatures) {
+                sb.append(feature);
+                sb.append(",");
+            }
+        } else {
+            sb.append("none,");
+        }
+
+        sb.append("isAlwaysOn:");
+        sb.append(mIsAlwaysOn);
+        sb.append(",");
+
+        sb.append("needsPointingToSatellite:");
+        sb.append(mNeedsPointingToSatellite);
+        sb.append(",");
+
+        sb.append("needsSeparateSimProfile:");
+        sb.append(mNeedsSeparateSimProfile);
+        return sb.toString();
+    }
+
+    @NonNull
+    public Set<Integer> getSupportedRadioTechnologies() {
+        return mSupportedRadioTechnologies;
+    }
+
+    public boolean isAlwaysOn() {
+        return mIsAlwaysOn;
+    }
+
+    /** Get function for mNeedsPointingToSatellite */
+    public boolean needsPointingToSatellite() {
+        return mNeedsPointingToSatellite;
+    }
+
+    @NonNull
+    public Set<Integer> getSupportedFeatures() {
+        return mSupportedFeatures;
+    }
+
+    /** Get function for mNeedsSeparateSimProfile */
+    public boolean needsSeparateSimProfile() {
+        return mNeedsSeparateSimProfile;
+    }
+
+    private void readFromParcel(Parcel in) {
+        mSupportedRadioTechnologies = new HashSet<>();
+        int numSupportedRadioTechnologies = in.readInt();
+        if (numSupportedRadioTechnologies > 0) {
+            for (int i = 0; i < numSupportedRadioTechnologies; i++) {
+                mSupportedRadioTechnologies.add(in.readInt());
+            }
+        }
+
+        mIsAlwaysOn = in.readBoolean();
+        mNeedsPointingToSatellite = in.readBoolean();
+
+        mSupportedFeatures = new HashSet<>();
+        int numSupportedFeatures = in.readInt();
+        if (numSupportedFeatures > 0) {
+            for (int i = 0; i < numSupportedFeatures; i++) {
+                mSupportedFeatures.add(in.readInt());
+            }
+        }
+
+        mNeedsSeparateSimProfile = in.readBoolean();
+    }
+}
diff --git a/telephony/java/android/telephony/satellite/stub/SatelliteImplBase.java b/telephony/java/android/telephony/satellite/stub/SatelliteImplBase.java
new file mode 100644
index 0000000..d3964a8
--- /dev/null
+++ b/telephony/java/android/telephony/satellite/stub/SatelliteImplBase.java
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.telephony.satellite.stub;
+
+import android.annotation.IntDef;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+
+
+/**
+ * @hide
+ */
+public class SatelliteImplBase {
+    private static final String TAG = "SatelliteImplBase";
+
+    /**@hide*/
+    @IntDef(
+            prefix = "TECHNOLOGY_",
+            value = {
+                    TECHNOLOGY_NB_IOT_NTN,
+                    TECHNOLOGY_NR_NTN,
+                    TECHNOLOGY_EMTC_NTN,
+                    TECHNOLOGY_PROPRIETARY
+            })
+    @Retention(RetentionPolicy.SOURCE)
+    public @interface NTRadioTechnology {}
+
+    /** 3GPP NB-IoT (Narrowband Internet of Things) over Non-Terrestrial-Networks technology */
+    public static final int TECHNOLOGY_NB_IOT_NTN =
+            android.hardware.radio.satellite.NTRadioTechnology.NB_IOT_NTN;
+    /** 3GPP 5G NR over Non-Terrestrial-Networks technology */
+    public static final int TECHNOLOGY_NR_NTN =
+            android.hardware.radio.satellite.NTRadioTechnology.NR_NTN;
+    /** 3GPP eMTC (enhanced Machine-Type Communication) over Non-Terrestrial-Networks technology */
+    public static final int TECHNOLOGY_EMTC_NTN =
+            android.hardware.radio.satellite.NTRadioTechnology.EMTC_NTN;
+    /** Proprietary technology like Iridium or Bullitt */
+    public static final int TECHNOLOGY_PROPRIETARY =
+            android.hardware.radio.satellite.NTRadioTechnology.PROPRIETARY;
+
+    /**@hide*/
+    @IntDef(
+            prefix = "FEATURE_",
+            value = {
+                    FEATURE_SOS_SMS,
+                    FEATURE_EMERGENCY_SMS,
+                    FEATURE_SMS,
+                    FEATURE_LOCATION_SHARING,
+                    FEATURE_UNKNOWN
+            })
+    @Retention(RetentionPolicy.SOURCE)
+    public @interface Feature {}
+
+    /** Able to send and receive SMS messages to/from SOS numbers like call/service centers */
+    public static final int FEATURE_SOS_SMS =
+            android.hardware.radio.satellite.SatelliteFeature.SOS_SMS;
+    /** Able to send and receive SMS messages to/from emergency numbers like 911 */
+    public static final int FEATURE_EMERGENCY_SMS =
+            android.hardware.radio.satellite.SatelliteFeature.EMERGENCY_SMS;
+    /** Able to send and receive SMS messages to/from any allowed contacts */
+    public static final int FEATURE_SMS = android.hardware.radio.satellite.SatelliteFeature.SMS;
+    /** Able to send device location to allowed contacts */
+    public static final int FEATURE_LOCATION_SHARING =
+            android.hardware.radio.satellite.SatelliteFeature.LOCATION_SHARING;
+    /** This feature is not defined in satellite HAL APIs */
+    public static final int FEATURE_UNKNOWN = 0xFFFF;
+
+    /**@hide*/
+    @IntDef(
+            prefix = "MODE_",
+            value = {
+                    MODE_POWERED_OFF,
+                    MODE_OUT_OF_SERVICE_NOT_SEARCHING,
+                    MODE_OUT_OF_SERVICE_SEARCHING,
+                    MODE_ACQUIRED,
+                    MODE_MESSAGE_TRANSFERRING
+            })
+    @Retention(RetentionPolicy.SOURCE)
+    public @interface Mode {}
+
+    /** Satellite modem is powered off */
+    public static final int MODE_POWERED_OFF =
+            android.hardware.radio.satellite.SatelliteMode.POWERED_OFF;
+    /** Satellite modem is in out of service state and not searching for satellite signal */
+    public static final int MODE_OUT_OF_SERVICE_NOT_SEARCHING =
+            android.hardware.radio.satellite.SatelliteMode.OUT_OF_SERVICE_NOT_SEARCHING;
+    /** Satellite modem is in out of service state and searching for satellite signal */
+    public static final int MODE_OUT_OF_SERVICE_SEARCHING =
+            android.hardware.radio.satellite.SatelliteMode.OUT_OF_SERVICE_SEARCHING;
+    /** Satellite modem has found satellite signal and gets connected to the satellite network */
+    public static final int MODE_ACQUIRED = android.hardware.radio.satellite.SatelliteMode.ACQUIRED;
+    /** Satellite modem is sending and/or receiving messages */
+    public static final int MODE_MESSAGE_TRANSFERRING =
+            android.hardware.radio.satellite.SatelliteMode.MESSAGE_TRANSFERRING;
+}
diff --git a/telephony/java/com/android/internal/telephony/RILConstants.java b/telephony/java/com/android/internal/telephony/RILConstants.java
index a9af199..6e56963 100644
--- a/telephony/java/com/android/internal/telephony/RILConstants.java
+++ b/telephony/java/com/android/internal/telephony/RILConstants.java
@@ -546,6 +546,22 @@
     int RIL_REQUEST_UPDATE_IMS_CALL_STATUS = 240;
     int RIL_REQUEST_SET_N1_MODE_ENABLED = 241;
     int RIL_REQUEST_IS_N1_MODE_ENABLED = 242;
+    int RIL_REQUEST_SET_LOCATION_PRIVACY_SETTING = 243;
+    int RIL_REQUEST_GET_LOCATION_PRIVACY_SETTING = 244;
+    int RIL_REQUEST_GET_SATELLITE_CAPABILITIES = 245;
+    int RIL_REQUEST_SET_SATELLITE_POWER = 246;
+    int RIL_REQUEST_GET_SATELLITE_POWER = 247;
+    int RIL_REQUEST_PROVISION_SATELLITE_SERVICE = 248;
+    int RIL_REQUEST_ADD_ALLOWED_SATELLITE_CONTACTS = 249;
+    int RIL_REQUEST_REMOVE_ALLOWED_SATELLITE_CONTACTS = 250;
+    int RIL_REQUEST_SEND_SATELLITE_MESSAGES = 251;
+    int RIL_REQUEST_GET_PENDING_SATELLITE_MESSAGES = 252;
+    int RIL_REQUEST_GET_SATELLITE_MODE = 253;
+    int RIL_REQUEST_SET_SATELLITE_INDICATION_FILTER = 254;
+    int RIL_REQUEST_START_SENDING_SATELLITE_POINTING_INFO = 255;
+    int RIL_REQUEST_STOP_SENDING_SATELLITE_POINTING_INFO = 256;
+    int RIL_REQUEST_GET_MAX_CHARACTERS_PER_SATELLITE_TEXT_MESSAGE = 257;
+    int RIL_REQUEST_GET_TIME_FOR_NEXT_SATELLITE_VISIBILITY = 258;
 
     /* Responses begin */
     int RIL_RESPONSE_ACKNOWLEDGEMENT = 800;
@@ -607,6 +623,13 @@
     int RIL_UNSOL_RESPONSE_SIM_PHONEBOOK_CHANGED = 1053;
     int RIL_UNSOL_RESPONSE_SIM_PHONEBOOK_RECORDS_RECEIVED = 1054;
     int RIL_UNSOL_SLICING_CONFIG_CHANGED = 1055;
+    int RIL_UNSOL_PENDING_SATELLITE_MESSAGE_COUNT = 1056;
+    int RIL_UNSOL_NEW_SATELLITE_MESSAGES = 1057;
+    int RIL_UNSOL_SATELLITE_MESSAGES_TRANSFER_COMPLETE = 1058;
+    int RIL_UNSOL_SATELLITE_POINTING_INFO_CHANGED = 1059;
+    int RIL_UNSOL_SATELLITE_MODE_CHANGED = 1060;
+    int RIL_UNSOL_SATELLITE_RADIO_TECHNOLOGY_CHANGED = 1061;
+    int RIL_UNSOL_SATELLITE_PROVISION_STATE_CHANGED = 1062;
 
     /* The following unsols are not defined in RIL.h */
     int RIL_UNSOL_HAL_NON_RIL_BASE = 1100;