diff options
9 files changed, 187 insertions, 13 deletions
diff --git a/data/etc/framework-sysconfig.xml b/data/etc/framework-sysconfig.xml index 7fafef754669..3a81c1309a8b 100644 --- a/data/etc/framework-sysconfig.xml +++ b/data/etc/framework-sysconfig.xml @@ -28,4 +28,6 @@ <backup-transport-whitelisted-service service="android/com.android.internal.backup.LocalTransportService" /> + <!-- Whitelist of bundled applications which all handle URLs to their websites by default --> + <app-link package="com.android.carrierdefaultapp" /> </config> diff --git a/packages/CarrierDefaultApp/AndroidManifest.xml b/packages/CarrierDefaultApp/AndroidManifest.xml index c30913393075..1cd7b6123e35 100644 --- a/packages/CarrierDefaultApp/AndroidManifest.xml +++ b/packages/CarrierDefaultApp/AndroidManifest.xml @@ -34,6 +34,7 @@ <intent-filter> <action android:name="com.android.internal.telephony.CARRIER_SIGNAL_REDIRECTED" /> <action android:name="com.android.internal.telephony.CARRIER_SIGNAL_RESET" /> + <action android:name="com.android.internal.telephony.CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE" /> <action android:name="android.intent.action.LOCALE_CHANGED" /> </intent-filter> </receiver> @@ -43,10 +44,24 @@ android:name="com.android.carrierdefaultapp.CaptivePortalLoginActivity" android:label="@string/action_bar_label" android:theme="@style/AppTheme" - android:configChanges="keyboardHidden|orientation|screenSize" > + android:configChanges="keyboardHidden|orientation|screenSize"> <intent-filter> <category android:name="android.intent.category.DEFAULT"/> </intent-filter> </activity> + + <activity-alias + android:name="com.android.carrierdefaultapp.URLHandlerActivity" + android:targetActivity="com.android.carrierdefaultapp.CaptivePortalLoginActivity" + android:enabled="false" > + <intent-filter> + <action android:name="android.intent.action.VIEW" /> + <category android:name="android.intent.category.DEFAULT"/> + <category android:name="android.intent.category.BROWSABLE" /> + <data android:scheme="http" /> + <data android:scheme="https" /> + <data android:host="*" /> + </intent-filter> + </activity-alias> </application> </manifest> diff --git a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CaptivePortalLoginActivity.java b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CaptivePortalLoginActivity.java index 6194b87dd76f..b0052cc73678 100644 --- a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CaptivePortalLoginActivity.java +++ b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CaptivePortalLoginActivity.java @@ -20,6 +20,9 @@ import android.app.Activity; import android.app.LoadedApk; import android.content.Context; import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; import android.graphics.Bitmap; import android.net.ConnectivityManager; import android.net.ConnectivityManager.NetworkCallback; @@ -34,6 +37,7 @@ import android.os.Bundle; import android.telephony.CarrierConfigManager; import android.telephony.Rlog; import android.telephony.SubscriptionManager; +import android.text.TextUtils; import android.util.ArrayMap; import android.util.Log; import android.util.TypedValue; @@ -68,7 +72,7 @@ public class CaptivePortalLoginActivity extends Activity { private static final boolean DBG = true; private static final int SOCKET_TIMEOUT_MS = 10 * 1000; - public static final int NETWORK_REQUEST_TIMEOUT_MS = 5 * 1000; + private static final int NETWORK_REQUEST_TIMEOUT_MS = 5 * 1000; private URL mUrl; private Network mNetwork; @@ -188,16 +192,19 @@ public class CaptivePortalLoginActivity extends Activity { CarrierActionUtils.applyCarrierAction( CarrierActionUtils.CARRIER_ACTION_CANCEL_ALL_NOTIFICATIONS, getIntent(), getApplicationContext()); - + CarrierActionUtils.applyCarrierAction( + CarrierActionUtils.CARRIER_ACTION_DISABLE_DEFAULT_URL_HANDLER, getIntent(), + getApplicationContext()); + CarrierActionUtils.applyCarrierAction( + CarrierActionUtils.CARRIER_ACTION_DEREGISTER_DEFAULT_NETWORK_AVAIL, getIntent(), + getApplicationContext()); } finishAndRemoveTask(); } private URL getUrlForCaptivePortal() { String url = getIntent().getStringExtra(TelephonyIntents.EXTRA_REDIRECTION_URL_KEY); - if (url.isEmpty()) { - url = mCm.getCaptivePortalServerUrl(); - } + if (TextUtils.isEmpty(url)) url = mCm.getCaptivePortalServerUrl(); final CarrierConfigManager configManager = getApplicationContext() .getSystemService(CarrierConfigManager.class); final int subId = getIntent().getIntExtra(PhoneConstants.SUBSCRIPTION_KEY, @@ -437,6 +444,27 @@ public class CaptivePortalLoginActivity extends Activity { } } + /** + * This alias presents the target activity, CaptivePortalLoginActivity, as a independent + * entity with its own intent filter to handle URL links. This alias will be enabled/disabled + * dynamically to handle url links based on the network conditions. + */ + public static String getAlias(Context context) { + try { + PackageInfo p = context.getPackageManager().getPackageInfo(context.getPackageName(), + PackageManager.GET_ACTIVITIES | PackageManager.MATCH_DISABLED_COMPONENTS); + for (ActivityInfo activityInfo : p.activities) { + String targetActivity = activityInfo.targetActivity; + if (CaptivePortalLoginActivity.class.getName().equals(targetActivity)) { + return activityInfo.name; + } + } + } catch (PackageManager.NameNotFoundException e) { + e.printStackTrace(); + } + return null; + } + private static void logd(String s) { Rlog.d(TAG, s); } diff --git a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CarrierActionUtils.java b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CarrierActionUtils.java index 021330650975..a2bf964ec05f 100644 --- a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CarrierActionUtils.java +++ b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CarrierActionUtils.java @@ -19,8 +19,10 @@ import android.app.Notification; import android.app.NotificationChannel; import android.app.NotificationManager; import android.app.PendingIntent; +import android.content.ComponentName; import android.content.Context; import android.content.Intent; +import android.content.pm.PackageManager; import android.content.res.Resources; import android.os.Bundle; import android.telephony.SubscriptionManager; @@ -49,6 +51,10 @@ public class CarrierActionUtils { public static final int CARRIER_ACTION_SHOW_PORTAL_NOTIFICATION = 4; public static final int CARRIER_ACTION_SHOW_NO_DATA_SERVICE_NOTIFICATION = 5; public static final int CARRIER_ACTION_CANCEL_ALL_NOTIFICATIONS = 6; + public static final int CARRIER_ACTION_ENABLE_DEFAULT_URL_HANDLER = 7; + public static final int CARRIER_ACTION_DISABLE_DEFAULT_URL_HANDLER = 8; + public static final int CARRIER_ACTION_REGISTER_DEFAULT_NETWORK_AVAIL = 9; + public static final int CARRIER_ACTION_DEREGISTER_DEFAULT_NETWORK_AVAIL = 10; public static void applyCarrierAction(int actionIdx, Intent intent, Context context) { switch (actionIdx) { @@ -73,6 +79,18 @@ public class CarrierActionUtils { case CARRIER_ACTION_CANCEL_ALL_NOTIFICATIONS: onCancelAllNotifications(context); break; + case CARRIER_ACTION_ENABLE_DEFAULT_URL_HANDLER: + onEnableDefaultURLHandler(context); + break; + case CARRIER_ACTION_DISABLE_DEFAULT_URL_HANDLER: + onDisableDefaultURLHandler(context); + break; + case CARRIER_ACTION_REGISTER_DEFAULT_NETWORK_AVAIL: + onRegisterDefaultNetworkAvail(intent, context); + break; + case CARRIER_ACTION_DEREGISTER_DEFAULT_NETWORK_AVAIL: + onDeregisterDefaultNetworkAvail(intent, context); + break; default: loge("unsupported carrier action index: " + actionIdx); } @@ -94,6 +112,38 @@ public class CarrierActionUtils { telephonyMgr.carrierActionSetMeteredApnsEnabled(subId, ENABLE); } + private static void onEnableDefaultURLHandler(Context context) { + logd("onEnableDefaultURLHandler"); + final PackageManager pm = context.getPackageManager(); + pm.setComponentEnabledSetting( + new ComponentName(context, CaptivePortalLoginActivity.getAlias(context)), + PackageManager.COMPONENT_ENABLED_STATE_ENABLED, PackageManager.DONT_KILL_APP); + } + + private static void onDisableDefaultURLHandler(Context context) { + logd("onDisableDefaultURLHandler"); + final PackageManager pm = context.getPackageManager(); + pm.setComponentEnabledSetting( + new ComponentName(context, CaptivePortalLoginActivity.getAlias(context)), + PackageManager.COMPONENT_ENABLED_STATE_DISABLED, PackageManager.DONT_KILL_APP); + } + + private static void onRegisterDefaultNetworkAvail(Intent intent, Context context) { + int subId = intent.getIntExtra(PhoneConstants.SUBSCRIPTION_KEY, + SubscriptionManager.getDefaultVoiceSubscriptionId()); + logd("onRegisterDefaultNetworkAvail subId: " + subId); + final TelephonyManager telephonyMgr = context.getSystemService(TelephonyManager.class); + telephonyMgr.carrierActionReportDefaultNetworkStatus(subId, true); + } + + private static void onDeregisterDefaultNetworkAvail(Intent intent, Context context) { + int subId = intent.getIntExtra(PhoneConstants.SUBSCRIPTION_KEY, + SubscriptionManager.getDefaultVoiceSubscriptionId()); + logd("onDeregisterDefaultNetworkAvail subId: " + subId); + final TelephonyManager telephonyMgr = context.getSystemService(TelephonyManager.class); + telephonyMgr.carrierActionReportDefaultNetworkStatus(subId, false); + } + private static void onDisableRadio(Intent intent, Context context) { int subId = intent.getIntExtra(PhoneConstants.SUBSCRIPTION_KEY, SubscriptionManager.getDefaultVoiceSubscriptionId()); diff --git a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CustomConfigLoader.java b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CustomConfigLoader.java index d5d0b7926c83..02c61d778086 100644 --- a/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CustomConfigLoader.java +++ b/packages/CarrierDefaultApp/src/com/android/carrierdefaultapp/CustomConfigLoader.java @@ -22,7 +22,6 @@ import android.telephony.CarrierConfigManager; import android.telephony.Rlog; import android.text.TextUtils; import android.util.Log; -import android.util.Pair; import com.android.internal.telephony.TelephonyIntents; import com.android.internal.util.ArrayUtils; @@ -95,6 +94,12 @@ public class CustomConfigLoader { configs = b.getStringArray(CarrierConfigManager .KEY_CARRIER_DEFAULT_ACTIONS_ON_RESET); break; + case TelephonyIntents.ACTION_CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE: + configs = b.getStringArray(CarrierConfigManager + .KEY_CARRIER_DEFAULT_ACTIONS_ON_DEFAULT_NETWORK_AVAILABLE); + arg1 = String.valueOf(intent.getBooleanExtra(TelephonyIntents + .EXTRA_DEFAULT_NETWORK_AVAILABLE_KEY, false)); + break; default: Rlog.e(TAG, "load carrier config failure with un-configured key: " + intent.getAction()); diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java index 3821b9cecaf6..bbda1c6194df 100644 --- a/telephony/java/android/telephony/CarrierConfigManager.java +++ b/telephony/java/android/telephony/CarrierConfigManager.java @@ -1022,6 +1022,26 @@ public class CarrierConfigManager { */ public static final String KEY_CARRIER_DEFAULT_ACTIONS_ON_RESET = "carrier_default_actions_on_reset_string_array"; + + /** + * Defines carrier-specific actions which act upon + * com.android.internal.telephony.CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE, + * used for customization of the default carrier app + * Format: + * { + * "true : CARRIER_ACTION_IDX_1", + * "false: CARRIER_ACTION_IDX_2" + * } + * Where {@code true} is a boolean indicates default network available/unavailable + * Where {@code CARRIER_ACTION_IDX} is an integer defined in + * {@link com.android.carrierdefaultapp.CarrierActionUtils CarrierActionUtils} + * Example: + * {@link com.android.carrierdefaultapp.CarrierActionUtils + * #CARRIER_ACTION_ENABLE_DEFAULT_URL_HANDLER enable the app as the default URL handler} + * @hide + */ + public static final String KEY_CARRIER_DEFAULT_ACTIONS_ON_DEFAULT_NETWORK_AVAILABLE = + "carrier_default_actions_on_default_network_available_string_array"; /** * Defines a list of acceptable redirection url for default carrier app * @hides @@ -1684,9 +1704,10 @@ public class CarrierConfigManager { sDefaults.putString(KEY_CARRIER_SETUP_APP_STRING, ""); sDefaults.putStringArray(KEY_CARRIER_APP_WAKE_SIGNAL_CONFIG_STRING_ARRAY, new String[]{ - "com.android.carrierdefaultapp/.CarrierDefaultBroadcastReceiver:" + - "com.android.internal.telephony.CARRIER_SIGNAL_REDIRECTED," + - "com.android.internal.telephony.CARRIER_SIGNAL_RESET" + "com.android.carrierdefaultapp/.CarrierDefaultBroadcastReceiver:" + + "com.android.internal.telephony.CARRIER_SIGNAL_REDIRECTED," + + "com.android.internal.telephony.CARRIER_SIGNAL_RESET," + + "com.android.internal.telephony.CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE" }); sDefaults.putStringArray(KEY_CARRIER_APP_NO_WAKE_SIGNAL_CONFIG_STRING_ARRAY, null); @@ -1694,12 +1715,22 @@ public class CarrierConfigManager { // Default carrier app configurations sDefaults.putStringArray(KEY_CARRIER_DEFAULT_ACTIONS_ON_REDIRECTION_STRING_ARRAY, new String[]{ - "4, 1" + "9, 4, 1" + //9: CARRIER_ACTION_REGISTER_NETWORK_AVAIL //4: CARRIER_ACTION_DISABLE_METERED_APNS //1: CARRIER_ACTION_SHOW_PORTAL_NOTIFICATION }); sDefaults.putStringArray(KEY_CARRIER_DEFAULT_ACTIONS_ON_RESET, new String[]{ - "6" //6: CARRIER_ACTION_CANCEL_ALL_NOTIFICATIONS + "6, 8" + //6: CARRIER_ACTION_CANCEL_ALL_NOTIFICATIONS + //8: CARRIER_ACTION_DISABLE_DEFAULT_URL_HANDLER + }); + sDefaults.putStringArray(KEY_CARRIER_DEFAULT_ACTIONS_ON_DEFAULT_NETWORK_AVAILABLE, + new String[] { + String.valueOf(false) + ": 7", + //7: CARRIER_ACTION_ENABLE_DEFAULT_URL_HANDLER + String.valueOf(true) + ": 8" + //8: CARRIER_ACTION_DISABLE_DEFAULT_URL_HANDLER }); sDefaults.putStringArray(KEY_CARRIER_DEFAULT_REDIRECTION_URL_STRING_ARRAY, null); diff --git a/telephony/java/android/telephony/TelephonyManager.java b/telephony/java/android/telephony/TelephonyManager.java index 190361bd59cd..e334c631d550 100644 --- a/telephony/java/android/telephony/TelephonyManager.java +++ b/telephony/java/android/telephony/TelephonyManager.java @@ -6661,6 +6661,25 @@ public class TelephonyManager { } /** + * Action set from carrier signalling broadcast receivers to start/stop reporting default + * network available events + * Permissions android.Manifest.permission.MODIFY_PHONE_STATE is required + * @param subId the subscription ID that this action applies to. + * @param report control start/stop reporting network status. + * @hide + */ + public void carrierActionReportDefaultNetworkStatus(int subId, boolean report) { + try { + ITelephony service = getITelephony(); + if (service != null) { + service.carrierActionReportDefaultNetworkStatus(subId, report); + } + } catch (RemoteException e) { + Log.e(TAG, "Error calling ITelephony#carrierActionReportDefaultNetworkStatus", e); + } + } + + /** * Get aggregated video call data usage since boot. * Permissions android.Manifest.permission.READ_NETWORK_USAGE_HISTORY is required. * diff --git a/telephony/java/com/android/internal/telephony/ITelephony.aidl b/telephony/java/com/android/internal/telephony/ITelephony.aidl index 654adb280310..9262ec5ed53b 100644 --- a/telephony/java/com/android/internal/telephony/ITelephony.aidl +++ b/telephony/java/com/android/internal/telephony/ITelephony.aidl @@ -1303,6 +1303,16 @@ interface ITelephony { void carrierActionSetRadioEnabled(int subId, boolean enabled); /** + * Action set from carrier signalling broadcast receivers to start/stop reporting default + * network conditions. + * Permissions android.Manifest.permission.MODIFY_PHONE_STATE is required + * @param subId the subscription ID that this action applies to. + * @param report control start/stop reporting default network events. + * @hide + */ + void carrierActionReportDefaultNetworkStatus(int subId, boolean report); + + /** * Get aggregated video call data usage since boot. * Permissions android.Manifest.permission.READ_NETWORK_USAGE_HISTORY is required. * diff --git a/telephony/java/com/android/internal/telephony/TelephonyIntents.java b/telephony/java/com/android/internal/telephony/TelephonyIntents.java index 034389088269..f29d993c55da 100644 --- a/telephony/java/com/android/internal/telephony/TelephonyIntents.java +++ b/telephony/java/com/android/internal/telephony/TelephonyIntents.java @@ -447,6 +447,20 @@ public class TelephonyIntents { "com.android.internal.telephony.CARRIER_SIGNAL_PCO_VALUE"; /** + * <p>Broadcast Action: when system default network available/unavailable with + * carrier-disabled mobile data. Intended for carrier apps to set/reset carrier actions when + * other network becomes system default network, Wi-Fi for example. + * The intent will have the following extra values:</p> + * <ul> + * <li>defaultNetworkAvailable</li><dd>A boolean indicates default network available.</dd> + * <li>subId</li><dd>Sub Id which associated the default data.</dd> + * </ul> + * <p class="note">This is a protected intent that can only be sent by the system. </p> + */ + public static final String ACTION_CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE = + "com.android.internal.telephony.CARRIER_SIGNAL_DEFAULT_NETWORK_AVAILABLE"; + + /** * <p>Broadcast Action: when framework reset all carrier actions on sim load or absent. * intended for carrier apps clean up (clear UI e.g.) and only sent to the specified carrier app * The intent will have the following extra values:</p> @@ -465,7 +479,7 @@ public class TelephonyIntents { public static final String EXTRA_APN_PROTO_KEY = "apnProto"; public static final String EXTRA_PCO_ID_KEY = "pcoId"; public static final String EXTRA_PCO_VALUE_KEY = "pcoValue"; - + public static final String EXTRA_DEFAULT_NETWORK_AVAILABLE_KEY = "defaultNetworkAvailable"; /** * Broadcast action to trigger CI OMA-DM Session. |