Merge "Add carrier to message title"
diff --git a/src/com/android/phone/CarrierConfigLoader.java b/src/com/android/phone/CarrierConfigLoader.java
index 1ea4180..cf7bafd 100644
--- a/src/com/android/phone/CarrierConfigLoader.java
+++ b/src/com/android/phone/CarrierConfigLoader.java
@@ -174,7 +174,7 @@
         @Override
         public void handleMessage(Message msg) {
             final int phoneId = msg.arg1;
-            log("mHandler: " + msg.what + " phoneId: " + phoneId);
+            logWithLocalLog("mHandler: " + msg.what + " phoneId: " + phoneId);
             switch (msg.what) {
                 case EVENT_CLEAR_CONFIG:
                 {
@@ -924,8 +924,12 @@
 
     @Override
     public void overrideConfig(int subscriptionId, PersistableBundle overrides) {
+        // SHELL UID already has MODIFY_PHONE_STATE implicitly so we do not have to check it, but
+        // the API signature explicitly declares that the method caller have MODIFY_PHONE_STATE, so
+        // calling this as well to be safe.
         mContext.enforceCallingOrSelfPermission(
                 android.Manifest.permission.MODIFY_PHONE_STATE, null);
+        TelephonyPermissions.enforceShellOnly(Binder.getCallingUid(), "overrideConfig");
         int phoneId = SubscriptionManager.getPhoneId(subscriptionId);
         if (!SubscriptionManager.isValidPhoneId(phoneId)) {
             log("Ignore invalid phoneId: " + phoneId + " for subId: " + subscriptionId);
@@ -942,7 +946,8 @@
         } else {
             mOverrideConfigs[phoneId].putAll(overrides);
         }
-        broadcastConfigChangedIntent(phoneId);
+
+        notifySubscriptionInfoUpdater(phoneId);
     }
 
     @Override
@@ -975,7 +980,7 @@
     public void updateConfigForPhoneId(int phoneId, String simState) {
         mContext.enforceCallingOrSelfPermission(
                 android.Manifest.permission.MODIFY_PHONE_STATE, null);
-        log("update config for phoneId: " + phoneId + " simState: " + simState);
+        logWithLocalLog("update config for phoneId: " + phoneId + " simState: " + simState);
         if (!SubscriptionManager.isValidPhoneId(phoneId)) {
             return;
         }
diff --git a/src/com/android/phone/NetworkScanHelper.java b/src/com/android/phone/NetworkScanHelper.java
index a21f547..fcfbf22 100644
--- a/src/com/android/phone/NetworkScanHelper.java
+++ b/src/com/android/phone/NetworkScanHelper.java
@@ -31,6 +31,7 @@
 import com.google.common.util.concurrent.FutureCallback;
 import com.google.common.util.concurrent.Futures;
 import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
 import com.google.common.util.concurrent.SettableFuture;
 
 import java.lang.annotation.Retention;
@@ -180,7 +181,7 @@
                     int errCode = Integer.parseInt(t.getMessage());
                     onError(errCode);
                 }
-            });
+            }, MoreExecutors.directExecutor());
             mExecutor.execute(new NetworkScanSyncTask(
                     mTelephonyManager, (SettableFuture) mNetworkScanFuture));
         } else if (type == NETWORK_SCAN_TYPE_INCREMENTAL_RESULTS) {
diff --git a/src/com/android/phone/PhoneInterfaceManager.java b/src/com/android/phone/PhoneInterfaceManager.java
index 1e689e6..46c2847 100755
--- a/src/com/android/phone/PhoneInterfaceManager.java
+++ b/src/com/android/phone/PhoneInterfaceManager.java
@@ -141,6 +141,7 @@
 import com.android.internal.telephony.SmsApplication.SmsApplicationData;
 import com.android.internal.telephony.SubscriptionController;
 import com.android.internal.telephony.TelephonyPermissions;
+import com.android.internal.telephony.dataconnection.ApnSettingUtils;
 import com.android.internal.telephony.emergency.EmergencyNumberTracker;
 import com.android.internal.telephony.euicc.EuiccConnector;
 import com.android.internal.telephony.ims.ImsResolver;
@@ -4448,9 +4449,14 @@
                 }
             }
         }
-        return mNetworkScanRequestTracker.startNetworkScan(
-                request, messenger, binder, getPhone(subId),
-                callingPackage);
+        final long identity = Binder.clearCallingIdentity();
+        try {
+            return mNetworkScanRequestTracker.startNetworkScan(
+                    request, messenger, binder, getPhone(subId),
+                    callingPackage);
+        } finally {
+            Binder.restoreCallingIdentity(identity);
+        }
     }
 
     private SecurityException checkNetworkRequestForSanitizedLocationAccess(
@@ -4470,16 +4476,6 @@
             }
         }
 
-        // STOPSHIP Revisit PLMN check (b/130253962).
-        //List<String> allowedMccMncs =
-        //        NetworkScanRequestTracker.getAllowedMccMncsForLocationRestrictedScan(mApp);
-        //for (String mccmnc : request.getPlmns()) {
-        //    if (!allowedMccMncs.contains(mccmnc)) {
-        //        return new SecurityException("Requested mccmnc " + mccmnc + " is not known to the"
-        //                + " device and cannot be scanned for without location access.");
-        //    }
-        //}
-
         return null;
     }
 
@@ -5549,6 +5545,7 @@
                                 .setCallingPid(Binder.getCallingPid())
                                 .setCallingUid(Binder.getCallingUid())
                                 .setMethod("getServiceStateForSubscriber")
+                                .setLogAsInfo(true)
                                 .setMinSdkVersionForFine(Build.VERSION_CODES.Q)
                                 .build());
 
@@ -5559,6 +5556,7 @@
                                 .setCallingPid(Binder.getCallingPid())
                                 .setCallingUid(Binder.getCallingUid())
                                 .setMethod("getServiceStateForSubscriber")
+                                .setLogAsInfo(true)
                                 .setMinSdkVersionForCoarse(Build.VERSION_CODES.Q)
                                 .build());
         // We don't care about hard or soft here -- all we need to know is how much info to scrub.
@@ -6936,4 +6934,56 @@
         if (hv.equals(HalVersion.UNKNOWN)) return -1;
         return hv.major * 100 + hv.minor;
     }
+
+    /**
+     * Return whether data is enabled for certain APN type. This will tell if framework will accept
+     * corresponding network requests on a subId.
+     *
+     *  Data is enabled if:
+     *  1) user data is turned on, or
+     *  2) APN is un-metered for this subscription, or
+     *  3) APN type is whitelisted. E.g. MMS is whitelisted if
+     *  {@link SubscriptionManager#setAlwaysAllowMmsData} is turned on.
+     *
+     * @return whether data is allowed for a apn type.
+     *
+     * @hide
+     */
+    @Override
+    public boolean isDataEnabledForApn(int apnType, int subId, String callingPackage) {
+        if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState(
+                mApp, subId, callingPackage, "isDataEnabledForApn")) {
+            throw new SecurityException("Needs READ_PHONE_STATE for isDataEnabledForApn");
+        }
+
+        // Now that all security checks passes, perform the operation as ourselves.
+        final long identity = Binder.clearCallingIdentity();
+        try {
+            Phone phone = getPhone(subId);
+            if (phone == null) return false;
+
+            boolean isMetered = ApnSettingUtils.isMeteredApnType(ApnSetting.getApnTypeString(
+                    apnType), phone);
+            return !isMetered || phone.getDataEnabledSettings().isDataEnabled(apnType);
+        } finally {
+            Binder.restoreCallingIdentity(identity);
+        }
+    }
+
+    @Override
+    public boolean isApnMetered(int apnType, int subId) {
+        enforceReadPrivilegedPermission("isApnMetered");
+
+        // Now that all security checks passes, perform the operation as ourselves.
+        final long identity = Binder.clearCallingIdentity();
+        try {
+            Phone phone = getPhone(subId);
+            if (phone == null) return true; // By default return true.
+
+            return ApnSettingUtils.isMeteredApnType(ApnSetting.getApnTypeString(
+                    apnType), phone);
+        } finally {
+            Binder.restoreCallingIdentity(identity);
+        }
+    }
 }
diff --git a/src/com/android/services/telephony/ImsConference.java b/src/com/android/services/telephony/ImsConference.java
index cada504..1f157e3 100644
--- a/src/com/android/services/telephony/ImsConference.java
+++ b/src/com/android/services/telephony/ImsConference.java
@@ -209,6 +209,11 @@
             Log.v(this, "onExtrasRemoved: c=" + c + " key=" + keys);
             removeExtras(keys);
         }
+
+        @Override
+        public void onConnectionEvent(Connection c, String event, Bundle extras) {
+            sendConnectionEvent(event, extras);
+        }
     };
 
     /**