CarrierSignalAgent.java revision c4ed983e8df098f4b3538e5114e8992f03cac095
14c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu/* 24c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * Copyright (C) 2016 The Android Open Source Project 34c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * 44c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * Licensed under the Apache License, Version 2.0 (the "License"); 54c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * you may not use this file except in compliance with the License. 64c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * You may obtain a copy of the License at 74c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * 84c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * http://www.apache.org/licenses/LICENSE-2.0 94c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * 104c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * Unless required by applicable law or agreed to in writing, software 114c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * distributed under the License is distributed on an "AS IS" BASIS, 124c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 134c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * See the License for the specific language governing permissions and 144c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * limitations under the License. 154c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 164c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxupackage com.android.internal.telephony; 174c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 184c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.content.ActivityNotFoundException; 194c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.content.ComponentName; 204c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.content.Context; 214c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.content.Intent; 224c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.content.pm.PackageManager; 234c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.os.PersistableBundle; 244c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.telephony.CarrierConfigManager; 254c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport android.telephony.Rlog; 264c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 274c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport com.android.internal.util.ArrayUtils; 284c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 294c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport java.util.HashMap; 304c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxuimport java.util.Map; 314c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 324c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu/** 334c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * This class act as an CarrierSignalling Agent. 344c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * it load registered carrier signalling receivers from Carrier Config and cache the result to avoid 354c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * repeated polling and send the intent to the interested receivers. 364c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * each CarrierSignalAgent is associated with a phone object. 374c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 384c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxupublic class CarrierSignalAgent { 394c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 404c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private static final String LOG_TAG = "CarrierSignalAgent"; 414c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private static final boolean DBG = true; 424c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 434c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** Member variables */ 444c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private final Phone mPhone; 454c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** 464c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * This is a map of intent action -> string array of carrier signal receiver names which are 474c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * interested in this intent action 484c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 49c4ed983e8df098f4b3538e5114e8992f03cac095fionaxu private final HashMap<String, String[]> mCachedCarrierSignalReceiverNames = 504c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu new HashMap<>(); 514c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** 524c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * This is a map of intent action -> carrier config key of signal receiver names which are 534c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * interested in this intent action 544c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 55c4ed983e8df098f4b3538e5114e8992f03cac095fionaxu private final Map<String, String> mIntentToCarrierConfigKeyMap = 564c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu new HashMap<String, String>() {{ 574c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu put(TelephonyIntents.ACTION_CARRIER_SIGNAL_REDIRECTED, 584c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu CarrierConfigManager.KEY_SIGNAL_REDIRECTION_RECEIVER_STRING_ARRAY); 594c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu put(TelephonyIntents.ACTION_CARRIER_SIGNAL_PCO_VALUE, 604c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu CarrierConfigManager.KEY_SIGNAL_PCO_RECEIVER_STRING_ARRAY); 614c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu put(TelephonyIntents.ACTION_CARRIER_SIGNAL_REQUEST_NETWORK_FAILED, 624c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu CarrierConfigManager.KEY_SIGNAL_DCFAILURE_RECEIVER_STRING_ARRAY); 634c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu }}; 644c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 654c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** Constructor */ 664c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu public CarrierSignalAgent(Phone phone) { 674c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu mPhone = phone; 684c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 694c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 704c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** 714c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * Read carrier signalling receiver name from CarrierConfig based on the intent type 724c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * @return array of receiver Name: the package (a String) name / the class (a String) name 734c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 744c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private String[] getCarrierSignalReceiverName(String intentAction) { 754c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu String receiverType = mIntentToCarrierConfigKeyMap.get(intentAction); 764c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if(receiverType == null) { 774c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return null; 784c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 794c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu String[] receiverNames = mCachedCarrierSignalReceiverNames.get(intentAction); 804c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu // In case of cache miss, we need to look up/load from carrier config. 814c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (!mCachedCarrierSignalReceiverNames.containsKey(intentAction)) { 824c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu CarrierConfigManager configManager = (CarrierConfigManager) mPhone.getContext() 834c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu .getSystemService(Context.CARRIER_CONFIG_SERVICE); 844c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu PersistableBundle b = null; 854c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (configManager != null) { 864c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu b = configManager.getConfig(); 874c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 884c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (b != null) { 894c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu receiverNames = b.getStringArray(receiverType); 904c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if(receiverNames!=null) { 914c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu for(String name: receiverNames) { 924c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu Rlog.d("loadCarrierSignalReceiverNames: ", name); 934c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 944c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 954c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 964c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu mCachedCarrierSignalReceiverNames.put(intentAction, receiverNames); 974c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 984c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return receiverNames; 994c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1004c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1014c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /** 1024c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu * Check if there are registered carrier broadcast receivers to handle any registered intents. 1034c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu */ 1044c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu public boolean hasRegisteredCarrierSignalReceivers() { 1054c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu for(String intent : mIntentToCarrierConfigKeyMap.keySet()) { 1064c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if(!ArrayUtils.isEmpty(getCarrierSignalReceiverName(intent))) { 1074c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return true; 1084c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1094c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1104c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return false; 1114c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1124c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1134c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu public boolean notifyCarrierSignalReceivers(Intent intent) { 1144c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu // Read a list of broadcast receivers from carrier config manager 1154c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu // which are interested on certain intent type 1164c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu String[] receiverName = getCarrierSignalReceiverName(intent.getAction()); 1174c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (receiverName == null) { 1184c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu loge("Carrier receiver name is null"); 1194c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return false; 1204c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1214c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu final PackageManager packageManager = mPhone.getContext().getPackageManager(); 1224c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu boolean ret = false; 1234c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1244c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu for(String name : receiverName) { 1254c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu ComponentName componentName = ComponentName.unflattenFromString(name); 1264c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (componentName == null) { 1274c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu loge("Carrier receiver name could not be parsed"); 1284c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return false; 1294c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1304c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu intent.setComponent(componentName); 1314c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu // Check if broadcast receiver is available 1324c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (packageManager.queryBroadcastReceivers(intent, 1334c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1344c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu loge("Carrier signal receiver is configured, but not available: " + name); 1354c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu break; 1364c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1374c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1384c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu intent.putExtra(PhoneConstants.SUBSCRIPTION_KEY, mPhone.getSubId()); 1394c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 1404c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1414c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu try { 1424c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu mPhone.getContext().sendBroadcast(intent); 1434c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu if (DBG) log("send Intent to carrier signal receiver with action: " + 1444c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu intent.getAction()); 1454c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu ret = true; 1464c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } catch (ActivityNotFoundException e) { 1474c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu loge("sendBroadcast failed: " + e); 1484c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1494c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1504c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1514c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu return ret; 1524c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1534c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1544c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu /* Clear cached receiver names */ 1554c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu public void reset() { 1564c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu mCachedCarrierSignalReceiverNames.clear(); 1574c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1584c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1594c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private void log(String s) { 1604c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu Rlog.d(LOG_TAG, "[" + mPhone.getPhoneId() + "]" + s); 1614c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1624c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu 1634c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu private void loge(String s) { 1644c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu Rlog.e(LOG_TAG, "[" + mPhone.getPhoneId() + "]" + s); 1654c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu } 1664c31e4c0d2db31fe84081aa6f1e2bcc08b31f9d3fionaxu} 167