Merge "Remove chatty logs"
diff --git a/src/com/android/phone/ImsUtil.java b/src/com/android/phone/ImsUtil.java
index 38936ec..0825cfb 100644
--- a/src/com/android/phone/ImsUtil.java
+++ b/src/com/android/phone/ImsUtil.java
@@ -25,6 +25,8 @@
 
 import com.android.ims.ImsConfig;
 import com.android.ims.ImsManager;
+import com.android.internal.telephony.PhoneFactory;
+import com.android.internal.telephony.imsphone.ImsPhone;
 
 public class ImsUtil {
     private static final String LOG_TAG = ImsUtil.class.getSimpleName();
@@ -128,6 +130,13 @@
             return false;
         }
 
+        // Do not promote WFC if in roaming and WFC roaming not allowed.
+        // WFC roaming setting is not modifiable, so its value is decided by the default value
+        // chosen by the carrier, hence it really means if the carrier supports WFC roaming.
+        if (getLastKnownRoamingState(phoneId) && !imsManager.isWfcRoamingEnabledByUser()) {
+            return false;
+        }
+
         ConnectivityManager cm =
                 (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
         if (cm != null) {
@@ -152,4 +161,13 @@
         }
         return subId;
     }
+
+    private static boolean getLastKnownRoamingState(int phoneId) {
+        try {
+            ImsPhone imsPhone = (ImsPhone) (PhoneFactory.getPhone(phoneId).getImsPhone());
+            return imsPhone.getRoamingState();
+        } catch (NullPointerException | ClassCastException e) {
+            return false;
+        }
+    }
 }
diff --git a/src/com/android/phone/PhoneInterfaceManager.java b/src/com/android/phone/PhoneInterfaceManager.java
index e348b84..52b8f0a 100755
--- a/src/com/android/phone/PhoneInterfaceManager.java
+++ b/src/com/android/phone/PhoneInterfaceManager.java
@@ -65,6 +65,7 @@
 import android.telecom.TelecomManager;
 import android.telephony.Annotation.ApnType;
 import android.telephony.CallForwardingInfo;
+import android.telephony.CarrierBandwidth;
 import android.telephony.CarrierConfigManager;
 import android.telephony.CarrierRestrictionRules;
 import android.telephony.CellIdentity;
@@ -5873,6 +5874,28 @@
     }
 
     /**
+     * get carrier bandwidth per primary and secondary carrier
+     * @param subId subscription id of the sim card
+     * @return CarrierBandwidth with bandwidth of both primary and secondary carrier..
+     */
+    @Override
+    public CarrierBandwidth getCarrierBandwidth(int subId) {
+        TelephonyPermissions
+                .enforeceCallingOrSelfReadPrivilegedPhoneStatePermissionOrCarrierPrivilege(
+                        mApp, subId, "isNRDualConnectivityEnabled");
+        WorkSource workSource = getWorkSource(Binder.getCallingUid());
+        final long identity = Binder.clearCallingIdentity();
+        try {
+            CarrierBandwidth carrierBandwidth =
+                    getPhoneFromSubId(subId).getCarrierBandwidth();
+            if (DBG) log("getCarrierBandwidth: " + carrierBandwidth);
+            return carrierBandwidth;
+        } finally {
+            Binder.restoreCallingIdentity(identity);
+        }
+    }
+
+    /**
      * Get the effective allowed network types on the device.
      * This API will return an intersection of allowed network types for all reasons,
      * including the configuration done through setAllowedNetworkTypes
diff --git a/src/com/android/services/telephony/TelephonyConnection.java b/src/com/android/services/telephony/TelephonyConnection.java
index 1caa8e7..09c83c0 100755
--- a/src/com/android/services/telephony/TelephonyConnection.java
+++ b/src/com/android/services/telephony/TelephonyConnection.java
@@ -96,6 +96,9 @@
     private static final int MSG_CONFERENCE_MERGE_FAILED = 6;
     private static final int MSG_SUPP_SERVICE_NOTIFY = 7;
 
+    // the threshold used to compare mAudioCodecBitrateKbps and mAudioCodecBandwidth.
+    private static final float THRESHOLD = 0.01f;
+
     /**
      * Mappings from {@link com.android.internal.telephony.Connection} extras keys to their
      * equivalents defined in {@link android.telecom.Connection}.
@@ -1496,7 +1499,8 @@
         }
     }
 
-    private void refreshCodecType() {
+    private void refreshCodec() {
+        boolean changed = false;
         Bundle newExtras = getExtras();
         if (newExtras == null) {
             newExtras = new Bundle();
@@ -1512,6 +1516,31 @@
                 Connection.AUDIO_CODEC_NONE);
         if (newCodecType != oldCodecType) {
             newExtras.putInt(Connection.EXTRA_AUDIO_CODEC, newCodecType);
+            changed = true;
+        }
+        if (isImsConnection()) {
+            float newBitrate = getOriginalConnection().getAudioCodecBitrateKbps();
+            float oldBitrate = newExtras.getFloat(Connection.EXTRA_AUDIO_CODEC_BITRATE_KBPS, 0.0f);
+            if (Math.abs(newBitrate - oldBitrate) > THRESHOLD) {
+                newExtras.putFloat(Connection.EXTRA_AUDIO_CODEC_BITRATE_KBPS, newBitrate);
+                changed = true;
+            }
+
+            float newBandwidth = getOriginalConnection().getAudioCodecBandwidthKhz();
+            float oldBandwidth = newExtras.getFloat(Connection.EXTRA_AUDIO_CODEC_BANDWIDTH_KHZ,
+                    0.0f);
+            if (Math.abs(newBandwidth - oldBandwidth) > THRESHOLD) {
+                newExtras.putFloat(Connection.EXTRA_AUDIO_CODEC_BANDWIDTH_KHZ, newBandwidth);
+                changed = true;
+            }
+        } else {
+            ArrayList<String> toRemove = new ArrayList<>();
+            toRemove.add(Connection.EXTRA_AUDIO_CODEC_BITRATE_KBPS);
+            toRemove.add(Connection.EXTRA_AUDIO_CODEC_BANDWIDTH_KHZ);
+            removeTelephonyExtras(toRemove);
+        }
+
+        if (changed) {
             putTelephonyExtras(newExtras);
         }
     }
@@ -2195,7 +2224,7 @@
         updateAddress();
         updateMultiparty();
         refreshDisableAddCall();
-        refreshCodecType();
+        refreshCodec();
     }
 
     /**