Merge 8c86f5bbccc30c6aee2f191f6695d127ce81871a on remote branch

Change-Id: Ic64163776c79df11ca2ccb2af23738d00c88c8c5
diff --git a/extphone/src/com/qti/extphone/ExtPhoneCallbackBase.java b/extphone/src/com/qti/extphone/ExtPhoneCallbackBase.java
index 38bb777..49e1ccf 100644
--- a/extphone/src/com/qti/extphone/ExtPhoneCallbackBase.java
+++ b/extphone/src/com/qti/extphone/ExtPhoneCallbackBase.java
@@ -41,6 +41,7 @@
 import android.util.Log;
 import com.qti.extphone.BearerAllocationStatus;
 import com.qti.extphone.DcParam;
+import com.qti.extphone.DualDataRecommendation;
 import com.qti.extphone.IExtPhoneCallback;
 import com.qti.extphone.NetworkSelectionMode;
 import com.qti.extphone.NrConfig;
@@ -269,4 +270,19 @@
     @Override
     public void onSimTypeChanged(QtiSimType[] simtype) throws RemoteException {
     }
+
+    @Override
+    public void onDualDataCapabilityChanged(Token token, Status status, boolean support)
+            throws RemoteException {
+    }
+
+    @Override
+    public void setDualDataUserPreferenceResponse(Token token, Status status)
+            throws RemoteException {
+    }
+
+    @Override
+    public void onDualDataRecommendation(DualDataRecommendation rec)
+            throws RemoteException {
+    }
 }
diff --git a/extphone/src/com/qti/extphone/ExtPhoneCallbackListener.java b/extphone/src/com/qti/extphone/ExtPhoneCallbackListener.java
index c27237c..e3016e2 100644
--- a/extphone/src/com/qti/extphone/ExtPhoneCallbackListener.java
+++ b/extphone/src/com/qti/extphone/ExtPhoneCallbackListener.java
@@ -15,6 +15,7 @@
 
 import com.qti.extphone.BearerAllocationStatus;
 import com.qti.extphone.DcParam;
+import com.qti.extphone.DualDataRecommendation;
 import com.qti.extphone.IExtPhoneCallback;
 import com.qti.extphone.NetworkSelectionMode;
 import com.qti.extphone.NrConfig;
@@ -72,6 +73,9 @@
     public static final int EVENT_START_NETWORK_SCAN_RESPONSE = 36;
     public static final int EVENT_STOP_NETWORK_SCAN_RESPONSE = 37;
     public static final int EVENT_ON_CIWLAN_CAPABILITY_CHANGE = 38;
+    public static final int EVENT_ON_DUAL_DATA_CAPABILITY_CHANGED = 39;
+    public static final int EVENT_SET_DUAL_DATA_USER_PREFERENCE_RESPONSE = 40;
+    public static final int EVENT_ON_DUAL_DATA_RECOMMENDATION = 41;
 
     private Handler mHandler;
     IExtPhoneCallback mCallback = new IExtPhoneCallbackStub(this);
@@ -483,6 +487,37 @@
                             Log.e(TAG, "EVENT_STOP_NETWORK_SCAN_RESPONSE : Exception = " + e);
                         }
                         break;
+                    case EVENT_ON_DUAL_DATA_CAPABILITY_CHANGED:
+                        try {
+                            IExtPhoneCallbackStub.Result result =
+                                    (IExtPhoneCallbackStub.Result) msg.obj;
+                            ExtPhoneCallbackListener.this.onDualDataCapabilityChanged(
+                                    result.mToken, result.mStatus, (boolean)result.mData);
+                        } catch (RemoteException e) {
+                            Log.e(TAG, "EVENT_ON_DUAL_DATA_CAPABILITY_CHANGED : Exception = " + e);
+                        }
+                        break;
+                    case EVENT_SET_DUAL_DATA_USER_PREFERENCE_RESPONSE:
+                        try {
+                            IExtPhoneCallbackStub.Result result =
+                                    (IExtPhoneCallbackStub.Result) msg.obj;
+                            ExtPhoneCallbackListener.this.setDualDataUserPreferenceResponse(
+                                    result.mToken, result.mStatus);
+                        } catch (RemoteException e) {
+                            Log.e(TAG, "EVENT_SET_DUAL_DATA_USER_PREFERENCE_RESPONSE :" +
+                                    "Exception = " + e);
+                        }
+                        break;
+                    case EVENT_ON_DUAL_DATA_RECOMMENDATION:
+                        try {
+                            IExtPhoneCallbackStub.Result result =
+                                    (IExtPhoneCallbackStub.Result) msg.obj;
+                            ExtPhoneCallbackListener.this.onDualDataRecommendation(
+                                    (DualDataRecommendation)result.mData);
+                        } catch (RemoteException e) {
+                            Log.e(TAG, "EVENT_ON_DUAL_DATA_RECOMMENDATION : Exception = " + e);
+                        }
+                        break;
                     default :
                         Log.d(TAG, "default : " + msg.what);
                 }
@@ -704,6 +739,22 @@
         Log.d(TAG, "UNIMPLEMENTED: onSimTypeChanged: simtype = " + simtype);
     }
 
+    public void onDualDataCapabilityChanged(Token token, Status status, boolean support)
+            throws RemoteException {
+        Log.d(TAG, "UNIMPLEMENTED: onDualDataCapabilityChanged: support = " + support);
+    }
+
+    public void setDualDataUserPreferenceResponse(Token token, Status status)
+            throws RemoteException {
+        Log.d(TAG, "UNIMPLEMENTED: setDualDataUserPreferenceResponse: token = "
+                + token + " status = " + status);
+    }
+
+    public void onDualDataRecommendation(DualDataRecommendation rec)
+            throws RemoteException {
+        Log.d(TAG, "UNIMPLEMENTED: onDualDataRecommendation: rec = " + rec);
+    }
+
     private static class IExtPhoneCallbackStub extends IExtPhoneCallback.Stub {
         private WeakReference<ExtPhoneCallbackListener> mExtPhoneCallbackListenerWeakRef;
 
@@ -960,6 +1011,27 @@
             send(EVENT_ON_SIM_TYPE_CHANGED, 0, 0, new Result(-1, null, null, -1, simtype));
         }
 
+        @Override
+        public void onDualDataCapabilityChanged(Token token, Status status, boolean support)
+                throws RemoteException {
+            send(EVENT_ON_DUAL_DATA_CAPABILITY_CHANGED, 0, 0,
+                    new Result(-1, token, status, -1, support));
+        }
+
+        @Override
+        public void setDualDataUserPreferenceResponse(Token token, Status status)
+                throws RemoteException {
+            send(EVENT_SET_DUAL_DATA_USER_PREFERENCE_RESPONSE, 0, 0,
+                    new Result(-1, token, status, -1, null));
+        }
+
+        @Override
+        public void onDualDataRecommendation(DualDataRecommendation rec)
+                throws RemoteException {
+            send(EVENT_ON_DUAL_DATA_RECOMMENDATION, 0, 0,
+                    new Result(-1, null, null, -1, rec));
+        }
+
         class Result {
             int mSlotId;
             Token mToken;
diff --git a/extphone/src/com/qti/extphone/ExtTelephonyManager.java b/extphone/src/com/qti/extphone/ExtTelephonyManager.java
index fc90c6a..5d85322 100644
--- a/extphone/src/com/qti/extphone/ExtTelephonyManager.java
+++ b/extphone/src/com/qti/extphone/ExtTelephonyManager.java
@@ -1099,6 +1099,50 @@
         return config;
     }
 
+    /**
+     * Request dual data capability.
+     * It is a static modem capability.
+     *
+     * @return - boolean TRUE/FALSE based on modem supporting dual data capability feature.
+     */
+    public boolean getDualDataCapability() {
+        if (isServiceConnected()) {
+            try {
+                return mExtTelephonyService.getDualDataCapability();
+            } catch (RemoteException ex) {
+                Log.e(LOG_TAG, "getDualDataCapability Failed.", ex);
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Set dual data user preference.
+     * In a multi-SIM device, inform modem if user wants dual data feature or not.
+     * Modem will not send any recommendations to HLOS to support dual data
+     * if user does not opt in the feature even if UE is dual data capable.
+     *
+     * @param client - Client registered with package name to receive callbacks.
+     * @param enable - Dual data selection opted by user. True if preference is enabled.
+     * @return - Integer Token can be used to compare with the response, null Token value
+     *        can be returned if request cannot be processed.
+     *
+     * Response function is IExtPhoneCallback#setDualDataUserPreferenceResponse().
+     */
+    public Token setDualDataUserPreference(Client client, boolean enable) throws RemoteException {
+        Token token = null;
+        if (!isServiceConnected()) {
+            Log.e(LOG_TAG, "service not connected!");
+            return token;
+        }
+        try {
+            token = mExtTelephonyService.setDualDataUserPreference(client, enable);
+        } catch (RemoteException e) {
+            Log.e(LOG_TAG, "setDualDataUserPreference ended in remote exception", e);
+        }
+        return token;
+    }
+
     public Client registerCallback(String packageName, IExtPhoneCallback callback) {
         Client client = null;
         if (!isServiceConnected()) {
diff --git a/extphone/src/com/qti/extphone/IExtPhone.aidl b/extphone/src/com/qti/extphone/IExtPhone.aidl
index 444f2c6..3ff300d 100644
--- a/extphone/src/com/qti/extphone/IExtPhone.aidl
+++ b/extphone/src/com/qti/extphone/IExtPhone.aidl
@@ -593,4 +593,27 @@
      * @return - The C_IWLAN configuration (only vs preferred) for home and roaming
      */
     CiwlanConfig getCiwlanConfig(int slotId);
+
+    /**
+     * Request dual data capability.
+     * It is a static modem capability.
+     *
+     * @return - boolean TRUE/FALSE based on modem supporting dual data capability feature.
+     */
+     boolean getDualDataCapability();
+
+    /**
+     * Set dual data user preference.
+     * In a multi-SIM device, inform modem if user wants dual data feature or not.
+     * Modem will not send any recommendations to HLOS to support dual data
+     * if user does not opt in the feature even if UE is dual data capable.
+     *
+     * @param client - Client registered with package name to receive callbacks.
+     * @param enable - Dual data selection opted by user. True if preference is enabled.
+     * @return - Integer Token can be used to compare with the response, null Token value
+     *        can be returned if request cannot be processed.
+     *
+     * Response function is IExtPhoneCallback#setDualDataUserPreferenceResponse().
+     */
+    Token setDualDataUserPreference(in Client client, in boolean enable);
 }
diff --git a/extphone/src/com/qti/extphone/IExtPhoneCallback.aidl b/extphone/src/com/qti/extphone/IExtPhoneCallback.aidl
index a068c52..751bffc 100644
--- a/extphone/src/com/qti/extphone/IExtPhoneCallback.aidl
+++ b/extphone/src/com/qti/extphone/IExtPhoneCallback.aidl
@@ -39,6 +39,7 @@
 import android.telephony.CellInfo;
 import com.qti.extphone.BearerAllocationStatus;
 import com.qti.extphone.DcParam;
+import com.qti.extphone.DualDataRecommendation;
 import com.qti.extphone.NetworkSelectionMode;
 import com.qti.extphone.NrConfig;
 import com.qti.extphone.NrConfigType;
@@ -359,4 +360,39 @@
      * @param - simtype array contains the current Sim Type on each Slot
      */
     void onSimTypeChanged(in QtiSimType[] simtype);
+
+    /**
+     * Response to getDualDataCapability and also called when dual data capability changes
+     *         in Modem.
+     *
+     * @param token to match request/response. Response must include same token as in request,
+     *         otherwise token is set to -1.
+     * @param status SUCCESS/FAILURE based on the modem result code
+     * @param support True if modem supports dual data feature.
+     */
+    void onDualDataCapabilityChanged(in Token token, in Status status, in boolean support);
+
+    /**
+     * Response to setDualDataUserPreference
+     * @param - token is the same token which is recived in
+     *          sendUserPreferenceForDataDuringVoiceCall
+     * @param - status SUCCESS/FAILURE based on RIL data module response
+     */
+    void setDualDataUserPreferenceResponse(in Token token, in Status status);
+
+    /**
+     * Received in the following conditions to allow/disallow internet pdn on nDDS
+     * after dual data user preference is sent as true
+     * to modem through IQtiRadioConfig#setDualDataUserPreference().
+     * Condition to send onDualDataRecommendation(NON_DDS and DATA_ALLOW):
+     *    1)UE is in DSDA sub-mode and in full concurrent condition
+     * Conditions to send onDualDataRecommendation(NON_DDS and DATA_DISALLOW):
+     *    1)UE is in DSDS sub-mode
+     *    2)UE is in TX sharing condition
+     *    3)IRAT is initiated on nDDS when UE is in L+NR RAT combo
+     *    4)nDDS is OOS
+     *
+     * @param rec <DualDataRecommendation> to allow/disallow internet pdn on nDDS.
+     */
+    void onDualDataRecommendation(in DualDataRecommendation rec);
 }