1 /* 2 * Copyright (C) 2006 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.phone; 18 19 import static com.android.internal.telephony.PhoneConstants.SUBSCRIPTION_KEY; 20 21 import android.Manifest.permission; 22 import android.app.AppOpsManager; 23 import android.app.PendingIntent; 24 import android.content.ComponentName; 25 import android.content.Context; 26 import android.content.Intent; 27 import android.content.SharedPreferences; 28 import android.content.pm.ComponentInfo; 29 import android.content.pm.PackageInfo; 30 import android.content.pm.PackageManager; 31 import android.net.NetworkStats; 32 import android.net.Uri; 33 import android.os.AsyncResult; 34 import android.os.Binder; 35 import android.os.Bundle; 36 import android.os.Handler; 37 import android.os.IBinder; 38 import android.os.Looper; 39 import android.os.Message; 40 import android.os.Messenger; 41 import android.os.PersistableBundle; 42 import android.os.RemoteException; 43 import android.os.ResultReceiver; 44 import android.os.ServiceManager; 45 import android.os.ShellCallback; 46 import android.os.SystemProperties; 47 import android.os.UserHandle; 48 import android.os.UserManager; 49 import android.os.WorkSource; 50 import android.preference.PreferenceManager; 51 import android.provider.Settings; 52 import android.service.carrier.CarrierIdentifier; 53 import android.telecom.PhoneAccount; 54 import android.telecom.PhoneAccountHandle; 55 import android.telecom.TelecomManager; 56 import android.telephony.CarrierConfigManager; 57 import android.telephony.CellInfo; 58 import android.telephony.ClientRequestStats; 59 import android.telephony.IccOpenLogicalChannelResponse; 60 import android.telephony.LocationAccessPolicy; 61 import android.telephony.ModemActivityInfo; 62 import android.telephony.NeighboringCellInfo; 63 import android.telephony.NetworkScanRequest; 64 import android.telephony.RadioAccessFamily; 65 import android.telephony.Rlog; 66 import android.telephony.ServiceState; 67 import android.telephony.SignalStrength; 68 import android.telephony.SmsManager; 69 import android.telephony.SubscriptionInfo; 70 import android.telephony.SubscriptionManager; 71 import android.telephony.TelephonyHistogram; 72 import android.telephony.TelephonyManager; 73 import android.telephony.UiccSlotInfo; 74 import android.telephony.UssdResponse; 75 import android.telephony.VisualVoicemailSmsFilterSettings; 76 import android.telephony.ims.aidl.IImsConfig; 77 import android.telephony.ims.aidl.IImsMmTelFeature; 78 import android.telephony.ims.aidl.IImsRcsFeature; 79 import android.telephony.ims.aidl.IImsRegistration; 80 import android.telephony.ims.stub.ImsRegistrationImplBase; 81 import android.text.TextUtils; 82 import android.util.ArraySet; 83 import android.util.EventLog; 84 import android.util.Log; 85 import android.util.Pair; 86 import android.util.Slog; 87 88 import com.android.ims.ImsManager; 89 import com.android.ims.internal.IImsServiceFeatureCallback; 90 import com.android.internal.telephony.CallManager; 91 import com.android.internal.telephony.CallStateException; 92 import com.android.internal.telephony.CarrierInfoManager; 93 import com.android.internal.telephony.CellNetworkScanResult; 94 import com.android.internal.telephony.CommandException; 95 import com.android.internal.telephony.DefaultPhoneNotifier; 96 import com.android.internal.telephony.ITelephony; 97 import com.android.internal.telephony.IccCard; 98 import com.android.internal.telephony.LocaleTracker; 99 import com.android.internal.telephony.MccTable; 100 import com.android.internal.telephony.NetworkScanRequestTracker; 101 import com.android.internal.telephony.OperatorInfo; 102 import com.android.internal.telephony.Phone; 103 import com.android.internal.telephony.PhoneConstantConversions; 104 import com.android.internal.telephony.PhoneConstants; 105 import com.android.internal.telephony.PhoneFactory; 106 import com.android.internal.telephony.ProxyController; 107 import com.android.internal.telephony.RIL; 108 import com.android.internal.telephony.RILConstants; 109 import com.android.internal.telephony.ServiceStateTracker; 110 import com.android.internal.telephony.SubscriptionController; 111 import com.android.internal.telephony.TelephonyPermissions; 112 import com.android.internal.telephony.euicc.EuiccConnector; 113 import com.android.internal.telephony.uicc.IccIoResult; 114 import com.android.internal.telephony.uicc.IccUtils; 115 import com.android.internal.telephony.uicc.SIMRecords; 116 import com.android.internal.telephony.uicc.UiccCard; 117 import com.android.internal.telephony.uicc.UiccCardApplication; 118 import com.android.internal.telephony.uicc.UiccController; 119 import com.android.internal.telephony.uicc.UiccProfile; 120 import com.android.internal.telephony.uicc.UiccSlot; 121 import com.android.internal.telephony.util.VoicemailNotificationSettingsUtil; 122 import com.android.internal.util.HexDump; 123 import com.android.phone.vvm.PhoneAccountHandleConverter; 124 import com.android.phone.vvm.RemoteVvmTaskManager; 125 import com.android.phone.vvm.VisualVoicemailSettingsUtil; 126 import com.android.phone.vvm.VisualVoicemailSmsFilterConfig; 127 128 import java.io.FileDescriptor; 129 import java.io.PrintWriter; 130 import java.nio.charset.StandardCharsets; 131 import java.util.ArrayList; 132 import java.util.Arrays; 133 import java.util.List; 134 import java.util.Locale; 135 import java.util.Map; 136 137 /** 138 * Implementation of the ITelephony interface. 139 */ 140 public class PhoneInterfaceManager extends ITelephony.Stub { 141 private static final String LOG_TAG = "PhoneInterfaceManager"; 142 private static final boolean DBG = (PhoneGlobals.DBG_LEVEL >= 2); 143 private static final boolean DBG_LOC = false; 144 private static final boolean DBG_MERGE = false; 145 146 // Message codes used with mMainThreadHandler 147 private static final int CMD_HANDLE_PIN_MMI = 1; 148 private static final int CMD_HANDLE_NEIGHBORING_CELL = 2; 149 private static final int EVENT_NEIGHBORING_CELL_DONE = 3; 150 private static final int CMD_ANSWER_RINGING_CALL = 4; 151 private static final int CMD_END_CALL = 5; // not used yet 152 private static final int CMD_TRANSMIT_APDU_LOGICAL_CHANNEL = 7; 153 private static final int EVENT_TRANSMIT_APDU_LOGICAL_CHANNEL_DONE = 8; 154 private static final int CMD_OPEN_CHANNEL = 9; 155 private static final int EVENT_OPEN_CHANNEL_DONE = 10; 156 private static final int CMD_CLOSE_CHANNEL = 11; 157 private static final int EVENT_CLOSE_CHANNEL_DONE = 12; 158 private static final int CMD_NV_READ_ITEM = 13; 159 private static final int EVENT_NV_READ_ITEM_DONE = 14; 160 private static final int CMD_NV_WRITE_ITEM = 15; 161 private static final int EVENT_NV_WRITE_ITEM_DONE = 16; 162 private static final int CMD_NV_WRITE_CDMA_PRL = 17; 163 private static final int EVENT_NV_WRITE_CDMA_PRL_DONE = 18; 164 private static final int CMD_NV_RESET_CONFIG = 19; 165 private static final int EVENT_NV_RESET_CONFIG_DONE = 20; 166 private static final int CMD_GET_PREFERRED_NETWORK_TYPE = 21; 167 private static final int EVENT_GET_PREFERRED_NETWORK_TYPE_DONE = 22; 168 private static final int CMD_SET_PREFERRED_NETWORK_TYPE = 23; 169 private static final int EVENT_SET_PREFERRED_NETWORK_TYPE_DONE = 24; 170 private static final int CMD_SEND_ENVELOPE = 25; 171 private static final int EVENT_SEND_ENVELOPE_DONE = 26; 172 private static final int CMD_INVOKE_OEM_RIL_REQUEST_RAW = 27; 173 private static final int EVENT_INVOKE_OEM_RIL_REQUEST_RAW_DONE = 28; 174 private static final int CMD_TRANSMIT_APDU_BASIC_CHANNEL = 29; 175 private static final int EVENT_TRANSMIT_APDU_BASIC_CHANNEL_DONE = 30; 176 private static final int CMD_EXCHANGE_SIM_IO = 31; 177 private static final int EVENT_EXCHANGE_SIM_IO_DONE = 32; 178 private static final int CMD_SET_VOICEMAIL_NUMBER = 33; 179 private static final int EVENT_SET_VOICEMAIL_NUMBER_DONE = 34; 180 private static final int CMD_SET_NETWORK_SELECTION_MODE_AUTOMATIC = 35; 181 private static final int EVENT_SET_NETWORK_SELECTION_MODE_AUTOMATIC_DONE = 36; 182 private static final int CMD_GET_MODEM_ACTIVITY_INFO = 37; 183 private static final int EVENT_GET_MODEM_ACTIVITY_INFO_DONE = 38; 184 private static final int CMD_PERFORM_NETWORK_SCAN = 39; 185 private static final int EVENT_PERFORM_NETWORK_SCAN_DONE = 40; 186 private static final int CMD_SET_NETWORK_SELECTION_MODE_MANUAL = 41; 187 private static final int EVENT_SET_NETWORK_SELECTION_MODE_MANUAL_DONE = 42; 188 private static final int CMD_SET_ALLOWED_CARRIERS = 43; 189 private static final int EVENT_SET_ALLOWED_CARRIERS_DONE = 44; 190 private static final int CMD_GET_ALLOWED_CARRIERS = 45; 191 private static final int EVENT_GET_ALLOWED_CARRIERS_DONE = 46; 192 private static final int CMD_HANDLE_USSD_REQUEST = 47; 193 private static final int CMD_GET_FORBIDDEN_PLMNS = 48; 194 private static final int EVENT_GET_FORBIDDEN_PLMNS_DONE = 49; 195 private static final int CMD_SWITCH_SLOTS = 50; 196 private static final int EVENT_SWITCH_SLOTS_DONE = 51; 197 198 // Parameters of select command. 199 private static final int SELECT_COMMAND = 0xA4; 200 private static final int SELECT_P1 = 0x04; 201 private static final int SELECT_P2 = 0; 202 private static final int SELECT_P3 = 0x10; 203 204 private static final String DEFAULT_NETWORK_MODE_PROPERTY_NAME = "ro.telephony.default_network"; 205 private static final String DEFAULT_DATA_ROAMING_PROPERTY_NAME = "ro.com.android.dataroaming"; 206 private static final String DEFAULT_MOBILE_DATA_PROPERTY_NAME = "ro.com.android.mobiledata"; 207 208 /** The singleton instance. */ 209 private static PhoneInterfaceManager sInstance; 210 211 private PhoneGlobals mApp; 212 private Phone mPhone; 213 private CallManager mCM; 214 private UserManager mUserManager; 215 private AppOpsManager mAppOps; 216 private MainThreadHandler mMainThreadHandler; 217 private SubscriptionController mSubscriptionController; 218 private SharedPreferences mTelephonySharedPreferences; 219 220 private static final String PREF_CARRIERS_ALPHATAG_PREFIX = "carrier_alphtag_"; 221 private static final String PREF_CARRIERS_NUMBER_PREFIX = "carrier_number_"; 222 private static final String PREF_CARRIERS_SUBSCRIBER_PREFIX = "carrier_subscriber_"; 223 224 // The AID of ISD-R. 225 private static final String ISDR_AID = "A0000005591010FFFFFFFF8900000100"; 226 227 private NetworkScanRequestTracker mNetworkScanRequestTracker; 228 229 /** 230 * A request object to use for transmitting data to an ICC. 231 */ 232 private static final class IccAPDUArgument { 233 public int channel, cla, command, p1, p2, p3; 234 public String data; 235 236 public IccAPDUArgument(int channel, int cla, int command, 237 int p1, int p2, int p3, String data) { 238 this.channel = channel; 239 this.cla = cla; 240 this.command = command; 241 this.p1 = p1; 242 this.p2 = p2; 243 this.p3 = p3; 244 this.data = data; 245 } 246 } 247 248 /** 249 * A request object to use for transmitting data to an ICC. 250 */ 251 private static final class ManualNetworkSelectionArgument { 252 public OperatorInfo operatorInfo; 253 public boolean persistSelection; 254 255 public ManualNetworkSelectionArgument(OperatorInfo operatorInfo, boolean persistSelection) { 256 this.operatorInfo = operatorInfo; 257 this.persistSelection = persistSelection; 258 } 259 } 260 261 /** 262 * A request object for use with {@link MainThreadHandler}. Requesters should wait() on the 263 * request after sending. The main thread will notify the request when it is complete. 264 */ 265 private static final class MainThreadRequest { 266 /** The argument to use for the request */ 267 public Object argument; 268 /** The result of the request that is run on the main thread */ 269 public Object result; 270 // The subscriber id that this request applies to. Defaults to 271 // SubscriptionManager.INVALID_SUBSCRIPTION_ID 272 public Integer subId = SubscriptionManager.INVALID_SUBSCRIPTION_ID; 273 274 public MainThreadRequest(Object argument) { 275 this.argument = argument; 276 } 277 278 public MainThreadRequest(Object argument, Integer subId) { 279 this.argument = argument; 280 if (subId != null) { 281 this.subId = subId; 282 } 283 } 284 } 285 286 private static final class IncomingThirdPartyCallArgs { 287 public final ComponentName component; 288 public final String callId; 289 public final String callerDisplayName; 290 291 public IncomingThirdPartyCallArgs(ComponentName component, String callId, 292 String callerDisplayName) { 293 this.component = component; 294 this.callId = callId; 295 this.callerDisplayName = callerDisplayName; 296 } 297 } 298 299 /** 300 * A handler that processes messages on the main thread in the phone process. Since many 301 * of the Phone calls are not thread safe this is needed to shuttle the requests from the 302 * inbound binder threads to the main thread in the phone process. The Binder thread 303 * may provide a {@link MainThreadRequest} object in the msg.obj field that they are waiting 304 * on, which will be notified when the operation completes and will contain the result of the 305 * request. 306 * 307 * <p>If a MainThreadRequest object is provided in the msg.obj field, 308 * note that request.result must be set to something non-null for the calling thread to 309 * unblock. 310 */ 311 private final class MainThreadHandler extends Handler { 312 @Override 313 public void handleMessage(Message msg) { 314 MainThreadRequest request; 315 Message onCompleted; 316 AsyncResult ar; 317 UiccCard uiccCard; 318 IccAPDUArgument iccArgument; 319 320 switch (msg.what) { 321 case CMD_HANDLE_USSD_REQUEST: { 322 request = (MainThreadRequest) msg.obj; 323 final Phone phone = getPhoneFromRequest(request); 324 Pair<String, ResultReceiver> ussdObject = (Pair) request.argument; 325 String ussdRequest = ussdObject.first; 326 ResultReceiver wrappedCallback = ussdObject.second; 327 328 if (!isUssdApiAllowed(request.subId)) { 329 // Carrier does not support use of this API, return failure. 330 Rlog.w(LOG_TAG, "handleUssdRequest: carrier does not support USSD apis."); 331 UssdResponse response = new UssdResponse(ussdRequest, null); 332 Bundle returnData = new Bundle(); 333 returnData.putParcelable(TelephonyManager.USSD_RESPONSE, response); 334 wrappedCallback.send(TelephonyManager.USSD_RETURN_FAILURE, returnData); 335 336 request.result = true; 337 synchronized (request) { 338 request.notifyAll(); 339 } 340 return; 341 } 342 343 try { 344 request.result = phone != null ? 345 phone.handleUssdRequest(ussdRequest, wrappedCallback) 346 : false; 347 } catch (CallStateException cse) { 348 request.result = false; 349 } 350 // Wake up the requesting thread 351 synchronized (request) { 352 request.notifyAll(); 353 } 354 break; 355 } 356 357 case CMD_HANDLE_PIN_MMI: { 358 request = (MainThreadRequest) msg.obj; 359 final Phone phone = getPhoneFromRequest(request); 360 request.result = phone != null ? 361 getPhoneFromRequest(request).handlePinMmi((String) request.argument) 362 : false; 363 // Wake up the requesting thread 364 synchronized (request) { 365 request.notifyAll(); 366 } 367 break; 368 } 369 370 case CMD_HANDLE_NEIGHBORING_CELL: 371 request = (MainThreadRequest) msg.obj; 372 onCompleted = obtainMessage(EVENT_NEIGHBORING_CELL_DONE, 373 request); 374 mPhone.getNeighboringCids(onCompleted, (WorkSource)request.argument); 375 break; 376 377 case EVENT_NEIGHBORING_CELL_DONE: 378 ar = (AsyncResult) msg.obj; 379 request = (MainThreadRequest) ar.userObj; 380 if (ar.exception == null && ar.result != null) { 381 request.result = ar.result; 382 } else { 383 // create an empty list to notify the waiting thread 384 request.result = new ArrayList<NeighboringCellInfo>(0); 385 } 386 // Wake up the requesting thread 387 synchronized (request) { 388 request.notifyAll(); 389 } 390 break; 391 392 case CMD_ANSWER_RINGING_CALL: 393 request = (MainThreadRequest) msg.obj; 394 int answer_subId = request.subId; 395 answerRingingCallInternal(answer_subId); 396 break; 397 398 case CMD_END_CALL: 399 request = (MainThreadRequest) msg.obj; 400 int end_subId = request.subId; 401 final boolean hungUp; 402 Phone phone = getPhone(end_subId); 403 if (phone == null) { 404 if (DBG) log("CMD_END_CALL: no phone for id: " + end_subId); 405 break; 406 } 407 int phoneType = phone.getPhoneType(); 408 if (phoneType == PhoneConstants.PHONE_TYPE_CDMA) { 409 // CDMA: If the user presses the Power button we treat it as 410 // ending the complete call session 411 hungUp = PhoneUtils.hangupRingingAndActive(getPhone(end_subId)); 412 } else if (phoneType == PhoneConstants.PHONE_TYPE_GSM) { 413 // GSM: End the call as per the Phone state 414 hungUp = PhoneUtils.hangup(mCM); 415 } else { 416 throw new IllegalStateException("Unexpected phone type: " + phoneType); 417 } 418 if (DBG) log("CMD_END_CALL: " + (hungUp ? "hung up!" : "no call to hang up")); 419 request.result = hungUp; 420 // Wake up the requesting thread 421 synchronized (request) { 422 request.notifyAll(); 423 } 424 break; 425 426 case CMD_TRANSMIT_APDU_LOGICAL_CHANNEL: 427 request = (MainThreadRequest) msg.obj; 428 iccArgument = (IccAPDUArgument) request.argument; 429 uiccCard = getUiccCardFromRequest(request); 430 if (uiccCard == null) { 431 loge("iccTransmitApduLogicalChannel: No UICC"); 432 request.result = new IccIoResult(0x6F, 0, (byte[])null); 433 synchronized (request) { 434 request.notifyAll(); 435 } 436 } else { 437 onCompleted = obtainMessage(EVENT_TRANSMIT_APDU_LOGICAL_CHANNEL_DONE, 438 request); 439 uiccCard.iccTransmitApduLogicalChannel( 440 iccArgument.channel, iccArgument.cla, iccArgument.command, 441 iccArgument.p1, iccArgument.p2, iccArgument.p3, iccArgument.data, 442 onCompleted); 443 } 444 break; 445 446 case EVENT_TRANSMIT_APDU_LOGICAL_CHANNEL_DONE: 447 ar = (AsyncResult) msg.obj; 448 request = (MainThreadRequest) ar.userObj; 449 if (ar.exception == null && ar.result != null) { 450 request.result = ar.result; 451 } else { 452 request.result = new IccIoResult(0x6F, 0, (byte[])null); 453 if (ar.result == null) { 454 loge("iccTransmitApduLogicalChannel: Empty response"); 455 } else if (ar.exception instanceof CommandException) { 456 loge("iccTransmitApduLogicalChannel: CommandException: " + 457 ar.exception); 458 } else { 459 loge("iccTransmitApduLogicalChannel: Unknown exception"); 460 } 461 } 462 synchronized (request) { 463 request.notifyAll(); 464 } 465 break; 466 467 case CMD_TRANSMIT_APDU_BASIC_CHANNEL: 468 request = (MainThreadRequest) msg.obj; 469 iccArgument = (IccAPDUArgument) request.argument; 470 uiccCard = getUiccCardFromRequest(request); 471 if (uiccCard == null) { 472 loge("iccTransmitApduBasicChannel: No UICC"); 473 request.result = new IccIoResult(0x6F, 0, (byte[])null); 474 synchronized (request) { 475 request.notifyAll(); 476 } 477 } else { 478 onCompleted = obtainMessage(EVENT_TRANSMIT_APDU_BASIC_CHANNEL_DONE, 479 request); 480 uiccCard.iccTransmitApduBasicChannel( 481 iccArgument.cla, iccArgument.command, iccArgument.p1, iccArgument.p2, 482 iccArgument.p3, iccArgument.data, onCompleted); 483 } 484 break; 485 486 case EVENT_TRANSMIT_APDU_BASIC_CHANNEL_DONE: 487 ar = (AsyncResult) msg.obj; 488 request = (MainThreadRequest) ar.userObj; 489 if (ar.exception == null && ar.result != null) { 490 request.result = ar.result; 491 } else { 492 request.result = new IccIoResult(0x6F, 0, (byte[])null); 493 if (ar.result == null) { 494 loge("iccTransmitApduBasicChannel: Empty response"); 495 } else if (ar.exception instanceof CommandException) { 496 loge("iccTransmitApduBasicChannel: CommandException: " + 497 ar.exception); 498 } else { 499 loge("iccTransmitApduBasicChannel: Unknown exception"); 500 } 501 } 502 synchronized (request) { 503 request.notifyAll(); 504 } 505 break; 506 507 case CMD_EXCHANGE_SIM_IO: 508 request = (MainThreadRequest) msg.obj; 509 iccArgument = (IccAPDUArgument) request.argument; 510 uiccCard = getUiccCardFromRequest(request); 511 if (uiccCard == null) { 512 loge("iccExchangeSimIO: No UICC"); 513 request.result = new IccIoResult(0x6F, 0, (byte[])null); 514 synchronized (request) { 515 request.notifyAll(); 516 } 517 } else { 518 onCompleted = obtainMessage(EVENT_EXCHANGE_SIM_IO_DONE, 519 request); 520 uiccCard.iccExchangeSimIO(iccArgument.cla, /* fileID */ 521 iccArgument.command, iccArgument.p1, iccArgument.p2, iccArgument.p3, 522 iccArgument.data, onCompleted); 523 } 524 break; 525 526 case EVENT_EXCHANGE_SIM_IO_DONE: 527 ar = (AsyncResult) msg.obj; 528 request = (MainThreadRequest) ar.userObj; 529 if (ar.exception == null && ar.result != null) { 530 request.result = ar.result; 531 } else { 532 request.result = new IccIoResult(0x6f, 0, (byte[])null); 533 } 534 synchronized (request) { 535 request.notifyAll(); 536 } 537 break; 538 539 case CMD_SEND_ENVELOPE: 540 request = (MainThreadRequest) msg.obj; 541 uiccCard = getUiccCardFromRequest(request); 542 if (uiccCard == null) { 543 loge("sendEnvelopeWithStatus: No UICC"); 544 request.result = new IccIoResult(0x6F, 0, (byte[])null); 545 synchronized (request) { 546 request.notifyAll(); 547 } 548 } else { 549 onCompleted = obtainMessage(EVENT_SEND_ENVELOPE_DONE, request); 550 uiccCard.sendEnvelopeWithStatus((String)request.argument, onCompleted); 551 } 552 break; 553 554 case EVENT_SEND_ENVELOPE_DONE: 555 ar = (AsyncResult) msg.obj; 556 request = (MainThreadRequest) ar.userObj; 557 if (ar.exception == null && ar.result != null) { 558 request.result = ar.result; 559 } else { 560 request.result = new IccIoResult(0x6F, 0, (byte[])null); 561 if (ar.result == null) { 562 loge("sendEnvelopeWithStatus: Empty response"); 563 } else if (ar.exception instanceof CommandException) { 564 loge("sendEnvelopeWithStatus: CommandException: " + 565 ar.exception); 566 } else { 567 loge("sendEnvelopeWithStatus: exception:" + ar.exception); 568 } 569 } 570 synchronized (request) { 571 request.notifyAll(); 572 } 573 break; 574 575 case CMD_OPEN_CHANNEL: 576 request = (MainThreadRequest) msg.obj; 577 uiccCard = getUiccCardFromRequest(request); 578 Pair<String, Integer> openChannelArgs = (Pair<String, Integer>) request.argument; 579 if (uiccCard == null) { 580 loge("iccOpenLogicalChannel: No UICC"); 581 request.result = new IccOpenLogicalChannelResponse(-1, 582 IccOpenLogicalChannelResponse.STATUS_MISSING_RESOURCE, null); 583 synchronized (request) { 584 request.notifyAll(); 585 } 586 } else { 587 onCompleted = obtainMessage(EVENT_OPEN_CHANNEL_DONE, request); 588 uiccCard.iccOpenLogicalChannel(openChannelArgs.first, 589 openChannelArgs.second, onCompleted); 590 } 591 break; 592 593 case EVENT_OPEN_CHANNEL_DONE: 594 ar = (AsyncResult) msg.obj; 595 request = (MainThreadRequest) ar.userObj; 596 IccOpenLogicalChannelResponse openChannelResp; 597 if (ar.exception == null && ar.result != null) { 598 int[] result = (int[]) ar.result; 599 int channelId = result[0]; 600 byte[] selectResponse = null; 601 if (result.length > 1) { 602 selectResponse = new byte[result.length - 1]; 603 for (int i = 1; i < result.length; ++i) { 604 selectResponse[i - 1] = (byte) result[i]; 605 } 606 } 607 openChannelResp = new IccOpenLogicalChannelResponse(channelId, 608 IccOpenLogicalChannelResponse.STATUS_NO_ERROR, selectResponse); 609 } else { 610 if (ar.result == null) { 611 loge("iccOpenLogicalChannel: Empty response"); 612 } 613 if (ar.exception != null) { 614 loge("iccOpenLogicalChannel: Exception: " + ar.exception); 615 } 616 617 int errorCode = IccOpenLogicalChannelResponse.STATUS_UNKNOWN_ERROR; 618 if (ar.exception instanceof CommandException) { 619 CommandException.Error error = 620 ((CommandException) (ar.exception)).getCommandError(); 621 if (error == CommandException.Error.MISSING_RESOURCE) { 622 errorCode = IccOpenLogicalChannelResponse.STATUS_MISSING_RESOURCE; 623 } else if (error == CommandException.Error.NO_SUCH_ELEMENT) { 624 errorCode = IccOpenLogicalChannelResponse.STATUS_NO_SUCH_ELEMENT; 625 } 626 } 627 openChannelResp = new IccOpenLogicalChannelResponse( 628 IccOpenLogicalChannelResponse.INVALID_CHANNEL, errorCode, null); 629 } 630 request.result = openChannelResp; 631 synchronized (request) { 632 request.notifyAll(); 633 } 634 break; 635 636 case CMD_CLOSE_CHANNEL: 637 request = (MainThreadRequest) msg.obj; 638 uiccCard = getUiccCardFromRequest(request); 639 if (uiccCard == null) { 640 loge("iccCloseLogicalChannel: No UICC"); 641 request.result = false; 642 synchronized (request) { 643 request.notifyAll(); 644 } 645 } else { 646 onCompleted = obtainMessage(EVENT_CLOSE_CHANNEL_DONE, request); 647 uiccCard.iccCloseLogicalChannel((Integer) request.argument, onCompleted); 648 } 649 break; 650 651 case EVENT_CLOSE_CHANNEL_DONE: 652 handleNullReturnEvent(msg, "iccCloseLogicalChannel"); 653 break; 654 655 case CMD_NV_READ_ITEM: 656 request = (MainThreadRequest) msg.obj; 657 onCompleted = obtainMessage(EVENT_NV_READ_ITEM_DONE, request); 658 mPhone.nvReadItem((Integer) request.argument, onCompleted); 659 break; 660 661 case EVENT_NV_READ_ITEM_DONE: 662 ar = (AsyncResult) msg.obj; 663 request = (MainThreadRequest) ar.userObj; 664 if (ar.exception == null && ar.result != null) { 665 request.result = ar.result; // String 666 } else { 667 request.result = ""; 668 if (ar.result == null) { 669 loge("nvReadItem: Empty response"); 670 } else if (ar.exception instanceof CommandException) { 671 loge("nvReadItem: CommandException: " + 672 ar.exception); 673 } else { 674 loge("nvReadItem: Unknown exception"); 675 } 676 } 677 synchronized (request) { 678 request.notifyAll(); 679 } 680 break; 681 682 case CMD_NV_WRITE_ITEM: 683 request = (MainThreadRequest) msg.obj; 684 onCompleted = obtainMessage(EVENT_NV_WRITE_ITEM_DONE, request); 685 Pair<Integer, String> idValue = (Pair<Integer, String>) request.argument; 686 mPhone.nvWriteItem(idValue.first, idValue.second, onCompleted); 687 break; 688 689 case EVENT_NV_WRITE_ITEM_DONE: 690 handleNullReturnEvent(msg, "nvWriteItem"); 691 break; 692 693 case CMD_NV_WRITE_CDMA_PRL: 694 request = (MainThreadRequest) msg.obj; 695 onCompleted = obtainMessage(EVENT_NV_WRITE_CDMA_PRL_DONE, request); 696 mPhone.nvWriteCdmaPrl((byte[]) request.argument, onCompleted); 697 break; 698 699 case EVENT_NV_WRITE_CDMA_PRL_DONE: 700 handleNullReturnEvent(msg, "nvWriteCdmaPrl"); 701 break; 702 703 case CMD_NV_RESET_CONFIG: 704 request = (MainThreadRequest) msg.obj; 705 onCompleted = obtainMessage(EVENT_NV_RESET_CONFIG_DONE, request); 706 mPhone.nvResetConfig((Integer) request.argument, onCompleted); 707 break; 708 709 case EVENT_NV_RESET_CONFIG_DONE: 710 handleNullReturnEvent(msg, "nvResetConfig"); 711 break; 712 713 case CMD_GET_PREFERRED_NETWORK_TYPE: 714 request = (MainThreadRequest) msg.obj; 715 onCompleted = obtainMessage(EVENT_GET_PREFERRED_NETWORK_TYPE_DONE, request); 716 getPhoneFromRequest(request).getPreferredNetworkType(onCompleted); 717 break; 718 719 case EVENT_GET_PREFERRED_NETWORK_TYPE_DONE: 720 ar = (AsyncResult) msg.obj; 721 request = (MainThreadRequest) ar.userObj; 722 if (ar.exception == null && ar.result != null) { 723 request.result = ar.result; // Integer 724 } else { 725 request.result = null; 726 if (ar.result == null) { 727 loge("getPreferredNetworkType: Empty response"); 728 } else if (ar.exception instanceof CommandException) { 729 loge("getPreferredNetworkType: CommandException: " + 730 ar.exception); 731 } else { 732 loge("getPreferredNetworkType: Unknown exception"); 733 } 734 } 735 synchronized (request) { 736 request.notifyAll(); 737 } 738 break; 739 740 case CMD_SET_PREFERRED_NETWORK_TYPE: 741 request = (MainThreadRequest) msg.obj; 742 onCompleted = obtainMessage(EVENT_SET_PREFERRED_NETWORK_TYPE_DONE, request); 743 int networkType = (Integer) request.argument; 744 getPhoneFromRequest(request).setPreferredNetworkType(networkType, onCompleted); 745 break; 746 747 case EVENT_SET_PREFERRED_NETWORK_TYPE_DONE: 748 handleNullReturnEvent(msg, "setPreferredNetworkType"); 749 break; 750 751 case CMD_INVOKE_OEM_RIL_REQUEST_RAW: 752 request = (MainThreadRequest)msg.obj; 753 onCompleted = obtainMessage(EVENT_INVOKE_OEM_RIL_REQUEST_RAW_DONE, request); 754 mPhone.invokeOemRilRequestRaw((byte[])request.argument, onCompleted); 755 break; 756 757 case EVENT_INVOKE_OEM_RIL_REQUEST_RAW_DONE: 758 ar = (AsyncResult)msg.obj; 759 request = (MainThreadRequest)ar.userObj; 760 request.result = ar; 761 synchronized (request) { 762 request.notifyAll(); 763 } 764 break; 765 766 case CMD_SET_VOICEMAIL_NUMBER: 767 request = (MainThreadRequest) msg.obj; 768 onCompleted = obtainMessage(EVENT_SET_VOICEMAIL_NUMBER_DONE, request); 769 Pair<String, String> tagNum = (Pair<String, String>) request.argument; 770 getPhoneFromRequest(request).setVoiceMailNumber(tagNum.first, tagNum.second, 771 onCompleted); 772 break; 773 774 case EVENT_SET_VOICEMAIL_NUMBER_DONE: 775 handleNullReturnEvent(msg, "setVoicemailNumber"); 776 break; 777 778 case CMD_SET_NETWORK_SELECTION_MODE_AUTOMATIC: 779 request = (MainThreadRequest) msg.obj; 780 onCompleted = obtainMessage(EVENT_SET_NETWORK_SELECTION_MODE_AUTOMATIC_DONE, 781 request); 782 getPhoneFromRequest(request).setNetworkSelectionModeAutomatic(onCompleted); 783 break; 784 785 case EVENT_SET_NETWORK_SELECTION_MODE_AUTOMATIC_DONE: 786 handleNullReturnEvent(msg, "setNetworkSelectionModeAutomatic"); 787 break; 788 789 case CMD_PERFORM_NETWORK_SCAN: 790 request = (MainThreadRequest) msg.obj; 791 onCompleted = obtainMessage(EVENT_PERFORM_NETWORK_SCAN_DONE, request); 792 getPhoneFromRequest(request).getAvailableNetworks(onCompleted); 793 break; 794 795 case EVENT_PERFORM_NETWORK_SCAN_DONE: 796 ar = (AsyncResult) msg.obj; 797 request = (MainThreadRequest) ar.userObj; 798 CellNetworkScanResult cellScanResult; 799 if (ar.exception == null && ar.result != null) { 800 cellScanResult = new CellNetworkScanResult( 801 CellNetworkScanResult.STATUS_SUCCESS, 802 (List<OperatorInfo>) ar.result); 803 } else { 804 if (ar.result == null) { 805 loge("getCellNetworkScanResults: Empty response"); 806 } 807 if (ar.exception != null) { 808 loge("getCellNetworkScanResults: Exception: " + ar.exception); 809 } 810 int errorCode = CellNetworkScanResult.STATUS_UNKNOWN_ERROR; 811 if (ar.exception instanceof CommandException) { 812 CommandException.Error error = 813 ((CommandException) (ar.exception)).getCommandError(); 814 if (error == CommandException.Error.RADIO_NOT_AVAILABLE) { 815 errorCode = CellNetworkScanResult.STATUS_RADIO_NOT_AVAILABLE; 816 } else if (error == CommandException.Error.GENERIC_FAILURE) { 817 errorCode = CellNetworkScanResult.STATUS_RADIO_GENERIC_FAILURE; 818 } 819 } 820 cellScanResult = new CellNetworkScanResult(errorCode, null); 821 } 822 request.result = cellScanResult; 823 synchronized (request) { 824 request.notifyAll(); 825 } 826 break; 827 828 case CMD_SET_NETWORK_SELECTION_MODE_MANUAL: 829 request = (MainThreadRequest) msg.obj; 830 ManualNetworkSelectionArgument selArg = 831 (ManualNetworkSelectionArgument) request.argument; 832 onCompleted = obtainMessage(EVENT_SET_NETWORK_SELECTION_MODE_MANUAL_DONE, 833 request); 834 getPhoneFromRequest(request).selectNetworkManually(selArg.operatorInfo, 835 selArg.persistSelection, onCompleted); 836 break; 837 838 case EVENT_SET_NETWORK_SELECTION_MODE_MANUAL_DONE: 839 handleNullReturnEvent(msg, "setNetworkSelectionModeManual"); 840 break; 841 842 case CMD_GET_MODEM_ACTIVITY_INFO: 843 request = (MainThreadRequest) msg.obj; 844 onCompleted = obtainMessage(EVENT_GET_MODEM_ACTIVITY_INFO_DONE, request); 845 mPhone.getModemActivityInfo(onCompleted); 846 break; 847 848 case EVENT_GET_MODEM_ACTIVITY_INFO_DONE: 849 ar = (AsyncResult) msg.obj; 850 request = (MainThreadRequest) ar.userObj; 851 if (ar.exception == null && ar.result != null) { 852 request.result = ar.result; 853 } else { 854 if (ar.result == null) { 855 loge("queryModemActivityInfo: Empty response"); 856 } else if (ar.exception instanceof CommandException) { 857 loge("queryModemActivityInfo: CommandException: " + 858 ar.exception); 859 } else { 860 loge("queryModemActivityInfo: Unknown exception"); 861 } 862 } 863 // Result cannot be null. Return ModemActivityInfo with all fields set to 0. 864 if (request.result == null) { 865 request.result = new ModemActivityInfo(0, 0, 0, null, 0, 0); 866 } 867 synchronized (request) { 868 request.notifyAll(); 869 } 870 break; 871 872 case CMD_SET_ALLOWED_CARRIERS: 873 request = (MainThreadRequest) msg.obj; 874 onCompleted = obtainMessage(EVENT_SET_ALLOWED_CARRIERS_DONE, request); 875 mPhone.setAllowedCarriers( 876 (List<CarrierIdentifier>) request.argument, 877 onCompleted); 878 break; 879 880 case EVENT_SET_ALLOWED_CARRIERS_DONE: 881 ar = (AsyncResult) msg.obj; 882 request = (MainThreadRequest) ar.userObj; 883 if (ar.exception == null && ar.result != null) { 884 request.result = ar.result; 885 } else { 886 if (ar.result == null) { 887 loge("setAllowedCarriers: Empty response"); 888 } else if (ar.exception instanceof CommandException) { 889 loge("setAllowedCarriers: CommandException: " + 890 ar.exception); 891 } else { 892 loge("setAllowedCarriers: Unknown exception"); 893 } 894 } 895 // Result cannot be null. Return -1 on error. 896 if (request.result == null) { 897 request.result = new int[]{-1}; 898 } 899 synchronized (request) { 900 request.notifyAll(); 901 } 902 break; 903 904 case CMD_GET_ALLOWED_CARRIERS: 905 request = (MainThreadRequest) msg.obj; 906 onCompleted = obtainMessage(EVENT_GET_ALLOWED_CARRIERS_DONE, request); 907 mPhone.getAllowedCarriers(onCompleted); 908 break; 909 910 case EVENT_GET_ALLOWED_CARRIERS_DONE: 911 ar = (AsyncResult) msg.obj; 912 request = (MainThreadRequest) ar.userObj; 913 if (ar.exception == null && ar.result != null) { 914 request.result = ar.result; 915 } else { 916 if (ar.result == null) { 917 loge("getAllowedCarriers: Empty response"); 918 } else if (ar.exception instanceof CommandException) { 919 loge("getAllowedCarriers: CommandException: " + 920 ar.exception); 921 } else { 922 loge("getAllowedCarriers: Unknown exception"); 923 } 924 } 925 // Result cannot be null. Return empty list of CarrierIdentifier. 926 if (request.result == null) { 927 request.result = new ArrayList<CarrierIdentifier>(0); 928 } 929 synchronized (request) { 930 request.notifyAll(); 931 } 932 break; 933 934 case EVENT_GET_FORBIDDEN_PLMNS_DONE: 935 ar = (AsyncResult) msg.obj; 936 request = (MainThreadRequest) ar.userObj; 937 if (ar.exception == null && ar.result != null) { 938 request.result = ar.result; 939 } else { 940 request.result = new IllegalArgumentException( 941 "Failed to retrieve Forbidden Plmns"); 942 if (ar.result == null) { 943 loge("getForbiddenPlmns: Empty response"); 944 } else { 945 loge("getForbiddenPlmns: Unknown exception"); 946 } 947 } 948 synchronized (request) { 949 request.notifyAll(); 950 } 951 break; 952 953 case CMD_GET_FORBIDDEN_PLMNS: 954 request = (MainThreadRequest) msg.obj; 955 uiccCard = getUiccCardFromRequest(request); 956 if (uiccCard == null) { 957 loge("getForbiddenPlmns() UiccCard is null"); 958 request.result = new IllegalArgumentException( 959 "getForbiddenPlmns() UiccCard is null"); 960 synchronized (request) { 961 request.notifyAll(); 962 } 963 break; 964 } 965 Integer appType = (Integer) request.argument; 966 UiccCardApplication uiccApp = uiccCard.getApplicationByType(appType); 967 if (uiccApp == null) { 968 loge("getForbiddenPlmns() no app with specified type -- " 969 + appType); 970 request.result = new IllegalArgumentException("Failed to get UICC App"); 971 synchronized (request) { 972 request.notifyAll(); 973 } 974 break; 975 } else { 976 if (DBG) logv("getForbiddenPlmns() found app " + uiccApp.getAid() 977 + " specified type -- " + appType); 978 } 979 onCompleted = obtainMessage(EVENT_GET_FORBIDDEN_PLMNS_DONE, request); 980 ((SIMRecords) uiccApp.getIccRecords()).getForbiddenPlmns( 981 onCompleted); 982 break; 983 984 case CMD_SWITCH_SLOTS: 985 request = (MainThreadRequest) msg.obj; 986 int[] physicalSlots = (int[]) request.argument; 987 onCompleted = obtainMessage(EVENT_SWITCH_SLOTS_DONE, request); 988 UiccController.getInstance().switchSlots(physicalSlots, onCompleted); 989 break; 990 991 case EVENT_SWITCH_SLOTS_DONE: 992 ar = (AsyncResult) msg.obj; 993 request = (MainThreadRequest) ar.userObj; 994 request.result = (ar.exception == null); 995 synchronized (request) { 996 request.notifyAll(); 997 } 998 break; 999 1000 default: 1001 Log.w(LOG_TAG, "MainThreadHandler: unexpected message code: " + msg.what); 1002 break; 1003 } 1004 } 1005 1006 private void handleNullReturnEvent(Message msg, String command) { 1007 AsyncResult ar = (AsyncResult) msg.obj; 1008 MainThreadRequest request = (MainThreadRequest) ar.userObj; 1009 if (ar.exception == null) { 1010 request.result = true; 1011 } else { 1012 request.result = false; 1013 if (ar.exception instanceof CommandException) { 1014 loge(command + ": CommandException: " + ar.exception); 1015 } else { 1016 loge(command + ": Unknown exception"); 1017 } 1018 } 1019 synchronized (request) { 1020 request.notifyAll(); 1021 } 1022 } 1023 } 1024 1025 /** 1026 * Posts the specified command to be executed on the main thread, 1027 * waits for the request to complete, and returns the result. 1028 * @see #sendRequestAsync 1029 */ 1030 private Object sendRequest(int command, Object argument) { 1031 return sendRequest(command, argument, SubscriptionManager.INVALID_SUBSCRIPTION_ID); 1032 } 1033 1034 /** 1035 * Posts the specified command to be executed on the main thread, 1036 * waits for the request to complete, and returns the result. 1037 * @see #sendRequestAsync 1038 */ 1039 private Object sendRequest(int command, Object argument, Integer subId) { 1040 if (Looper.myLooper() == mMainThreadHandler.getLooper()) { 1041 throw new RuntimeException("This method will deadlock if called from the main thread."); 1042 } 1043 1044 MainThreadRequest request = new MainThreadRequest(argument, subId); 1045 Message msg = mMainThreadHandler.obtainMessage(command, request); 1046 msg.sendToTarget(); 1047 1048 // Wait for the request to complete 1049 synchronized (request) { 1050 while (request.result == null) { 1051 try { 1052 request.wait(); 1053 } catch (InterruptedException e) { 1054 // Do nothing, go back and wait until the request is complete 1055 } 1056 } 1057 } 1058 return request.result; 1059 } 1060 1061 /** 1062 * Asynchronous ("fire and forget") version of sendRequest(): 1063 * Posts the specified command to be executed on the main thread, and 1064 * returns immediately. 1065 * @see #sendRequest 1066 */ 1067 private void sendRequestAsync(int command) { 1068 mMainThreadHandler.sendEmptyMessage(command); 1069 } 1070 1071 /** 1072 * Same as {@link #sendRequestAsync(int)} except it takes an argument. 1073 * @see {@link #sendRequest(int,Object)} 1074 */ 1075 private void sendRequestAsync(int command, Object argument) { 1076 MainThreadRequest request = new MainThreadRequest(argument); 1077 Message msg = mMainThreadHandler.obtainMessage(command, request); 1078 msg.sendToTarget(); 1079 } 1080 1081 /** 1082 * Initialize the singleton PhoneInterfaceManager instance. 1083 * This is only done once, at startup, from PhoneApp.onCreate(). 1084 */ 1085 /* package */ static PhoneInterfaceManager init(PhoneGlobals app, Phone phone) { 1086 synchronized (PhoneInterfaceManager.class) { 1087 if (sInstance == null) { 1088 sInstance = new PhoneInterfaceManager(app, phone); 1089 } else { 1090 Log.wtf(LOG_TAG, "init() called multiple times! sInstance = " + sInstance); 1091 } 1092 return sInstance; 1093 } 1094 } 1095 1096 /** Private constructor; @see init() */ 1097 private PhoneInterfaceManager(PhoneGlobals app, Phone phone) { 1098 mApp = app; 1099 mPhone = phone; 1100 mCM = PhoneGlobals.getInstance().mCM; 1101 mUserManager = (UserManager) app.getSystemService(Context.USER_SERVICE); 1102 mAppOps = (AppOpsManager)app.getSystemService(Context.APP_OPS_SERVICE); 1103 mMainThreadHandler = new MainThreadHandler(); 1104 mTelephonySharedPreferences = 1105 PreferenceManager.getDefaultSharedPreferences(mPhone.getContext()); 1106 mSubscriptionController = SubscriptionController.getInstance(); 1107 mNetworkScanRequestTracker = new NetworkScanRequestTracker(); 1108 1109 publish(); 1110 } 1111 1112 private void publish() { 1113 if (DBG) log("publish: " + this); 1114 1115 ServiceManager.addService("phone", this); 1116 } 1117 1118 private Phone getPhoneFromRequest(MainThreadRequest request) { 1119 return (request.subId == SubscriptionManager.INVALID_SUBSCRIPTION_ID) 1120 ? mPhone : getPhone(request.subId); 1121 } 1122 1123 private UiccCard getUiccCardFromRequest(MainThreadRequest request) { 1124 Phone phone = getPhoneFromRequest(request); 1125 return phone == null ? null : 1126 UiccController.getInstance().getUiccCard(phone.getPhoneId()); 1127 } 1128 1129 // returns phone associated with the subId. 1130 private Phone getPhone(int subId) { 1131 return PhoneFactory.getPhone(mSubscriptionController.getPhoneId(subId)); 1132 } 1133 // 1134 // Implementation of the ITelephony interface. 1135 // 1136 1137 public void dial(String number) { 1138 dialForSubscriber(getPreferredVoiceSubscription(), number); 1139 } 1140 1141 public void dialForSubscriber(int subId, String number) { 1142 if (DBG) log("dial: " + number); 1143 // No permission check needed here: This is just a wrapper around the 1144 // ACTION_DIAL intent, which is available to any app since it puts up 1145 // the UI before it does anything. 1146 1147 String url = createTelUrl(number); 1148 if (url == null) { 1149 return; 1150 } 1151 1152 // PENDING: should we just silently fail if phone is offhook or ringing? 1153 PhoneConstants.State state = mCM.getState(subId); 1154 if (state != PhoneConstants.State.OFFHOOK && state != PhoneConstants.State.RINGING) { 1155 Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(url)); 1156 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 1157 mApp.startActivity(intent); 1158 } 1159 } 1160 1161 public void call(String callingPackage, String number) { 1162 callForSubscriber(getPreferredVoiceSubscription(), callingPackage, number); 1163 } 1164 1165 public void callForSubscriber(int subId, String callingPackage, String number) { 1166 if (DBG) log("call: " + number); 1167 1168 // This is just a wrapper around the ACTION_CALL intent, but we still 1169 // need to do a permission check since we're calling startActivity() 1170 // from the context of the phone app. 1171 enforceCallPermission(); 1172 1173 if (mAppOps.noteOp(AppOpsManager.OP_CALL_PHONE, Binder.getCallingUid(), callingPackage) 1174 != AppOpsManager.MODE_ALLOWED) { 1175 return; 1176 } 1177 1178 String url = createTelUrl(number); 1179 if (url == null) { 1180 return; 1181 } 1182 1183 boolean isValid = false; 1184 final List<SubscriptionInfo> slist = getActiveSubscriptionInfoList(); 1185 if (slist != null) { 1186 for (SubscriptionInfo subInfoRecord : slist) { 1187 if (subInfoRecord.getSubscriptionId() == subId) { 1188 isValid = true; 1189 break; 1190 } 1191 } 1192 } 1193 if (isValid == false) { 1194 return; 1195 } 1196 1197 Intent intent = new Intent(Intent.ACTION_CALL, Uri.parse(url)); 1198 intent.putExtra(SUBSCRIPTION_KEY, subId); 1199 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 1200 mApp.startActivity(intent); 1201 } 1202 1203 /** 1204 * End a call based on call state 1205 * @return true is a call was ended 1206 */ 1207 public boolean endCall() { 1208 return endCallForSubscriber(getDefaultSubscription()); 1209 } 1210 1211 /** 1212 * End a call based on the call state of the subId 1213 * @return true is a call was ended 1214 */ 1215 public boolean endCallForSubscriber(int subId) { 1216 if (mApp.checkCallingOrSelfPermission(permission.MODIFY_PHONE_STATE) 1217 != PackageManager.PERMISSION_GRANTED) { 1218 Log.i(LOG_TAG, "endCall: called without modify phone state."); 1219 EventLog.writeEvent(0x534e4554, "67862398", -1, ""); 1220 throw new SecurityException("MODIFY_PHONE_STATE permission required."); 1221 } 1222 return (Boolean) sendRequest(CMD_END_CALL, null, new Integer(subId)); 1223 } 1224 1225 public void answerRingingCall() { 1226 answerRingingCallForSubscriber(getDefaultSubscription()); 1227 } 1228 1229 public void answerRingingCallForSubscriber(int subId) { 1230 if (DBG) log("answerRingingCall..."); 1231 // TODO: there should eventually be a separate "ANSWER_PHONE" permission, 1232 // but that can probably wait till the big TelephonyManager API overhaul. 1233 // For now, protect this call with the MODIFY_PHONE_STATE permission. 1234 enforceModifyPermission(); 1235 sendRequest(CMD_ANSWER_RINGING_CALL, null, new Integer(subId)); 1236 } 1237 1238 /** 1239 * Make the actual telephony calls to implement answerRingingCall(). 1240 * This should only be called from the main thread of the Phone app. 1241 * @see #answerRingingCall 1242 * 1243 * TODO: it would be nice to return true if we answered the call, or 1244 * false if there wasn't actually a ringing incoming call, or some 1245 * other error occurred. (In other words, pass back the return value 1246 * from PhoneUtils.answerCall() or PhoneUtils.answerAndEndActive().) 1247 * But that would require calling this method via sendRequest() rather 1248 * than sendRequestAsync(), and right now we don't actually *need* that 1249 * return value, so let's just return void for now. 1250 */ 1251 private void answerRingingCallInternal(int subId) { 1252 final boolean hasRingingCall = !getPhone(subId).getRingingCall().isIdle(); 1253 if (hasRingingCall) { 1254 final boolean hasActiveCall = !getPhone(subId).getForegroundCall().isIdle(); 1255 final boolean hasHoldingCall = !getPhone(subId).getBackgroundCall().isIdle(); 1256 if (hasActiveCall && hasHoldingCall) { 1257 // Both lines are in use! 1258 // TODO: provide a flag to let the caller specify what 1259 // policy to use if both lines are in use. (The current 1260 // behavior is hardwired to "answer incoming, end ongoing", 1261 // which is how the CALL button is specced to behave.) 1262 PhoneUtils.answerAndEndActive(mCM, mCM.getFirstActiveRingingCall()); 1263 return; 1264 } else { 1265 // answerCall() will automatically hold the current active 1266 // call, if there is one. 1267 PhoneUtils.answerCall(mCM.getFirstActiveRingingCall()); 1268 return; 1269 } 1270 } else { 1271 // No call was ringing. 1272 return; 1273 } 1274 } 1275 1276 /** 1277 * This method is no longer used and can be removed once TelephonyManager stops referring to it. 1278 */ 1279 public void silenceRinger() { 1280 Log.e(LOG_TAG, "silenseRinger not supported"); 1281 } 1282 1283 @Override 1284 public boolean isOffhook(String callingPackage) { 1285 return isOffhookForSubscriber(getDefaultSubscription(), callingPackage); 1286 } 1287 1288 @Override 1289 public boolean isOffhookForSubscriber(int subId, String callingPackage) { 1290 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1291 mApp, subId, callingPackage, "isOffhookForSubscriber")) { 1292 return false; 1293 } 1294 1295 final Phone phone = getPhone(subId); 1296 if (phone != null) { 1297 return (phone.getState() == PhoneConstants.State.OFFHOOK); 1298 } else { 1299 return false; 1300 } 1301 } 1302 1303 @Override 1304 public boolean isRinging(String callingPackage) { 1305 return (isRingingForSubscriber(getDefaultSubscription(), callingPackage)); 1306 } 1307 1308 @Override 1309 public boolean isRingingForSubscriber(int subId, String callingPackage) { 1310 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1311 mApp, subId, callingPackage, "isRingingForSubscriber")) { 1312 return false; 1313 } 1314 1315 final Phone phone = getPhone(subId); 1316 if (phone != null) { 1317 return (phone.getState() == PhoneConstants.State.RINGING); 1318 } else { 1319 return false; 1320 } 1321 } 1322 1323 @Override 1324 public boolean isIdle(String callingPackage) { 1325 return isIdleForSubscriber(getDefaultSubscription(), callingPackage); 1326 } 1327 1328 @Override 1329 public boolean isIdleForSubscriber(int subId, String callingPackage) { 1330 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1331 mApp, subId, callingPackage, "isIdleForSubscriber")) { 1332 return false; 1333 } 1334 1335 final Phone phone = getPhone(subId); 1336 if (phone != null) { 1337 return (phone.getState() == PhoneConstants.State.IDLE); 1338 } else { 1339 return false; 1340 } 1341 } 1342 1343 public boolean supplyPin(String pin) { 1344 return supplyPinForSubscriber(getDefaultSubscription(), pin); 1345 } 1346 1347 public boolean supplyPinForSubscriber(int subId, String pin) { 1348 int [] resultArray = supplyPinReportResultForSubscriber(subId, pin); 1349 return (resultArray[0] == PhoneConstants.PIN_RESULT_SUCCESS) ? true : false; 1350 } 1351 1352 public boolean supplyPuk(String puk, String pin) { 1353 return supplyPukForSubscriber(getDefaultSubscription(), puk, pin); 1354 } 1355 1356 public boolean supplyPukForSubscriber(int subId, String puk, String pin) { 1357 int [] resultArray = supplyPukReportResultForSubscriber(subId, puk, pin); 1358 return (resultArray[0] == PhoneConstants.PIN_RESULT_SUCCESS) ? true : false; 1359 } 1360 1361 /** {@hide} */ 1362 public int[] supplyPinReportResult(String pin) { 1363 return supplyPinReportResultForSubscriber(getDefaultSubscription(), pin); 1364 } 1365 1366 public int[] supplyPinReportResultForSubscriber(int subId, String pin) { 1367 enforceModifyPermission(); 1368 final UnlockSim checkSimPin = new UnlockSim(getPhone(subId).getIccCard()); 1369 checkSimPin.start(); 1370 return checkSimPin.unlockSim(null, pin); 1371 } 1372 1373 /** {@hide} */ 1374 public int[] supplyPukReportResult(String puk, String pin) { 1375 return supplyPukReportResultForSubscriber(getDefaultSubscription(), puk, pin); 1376 } 1377 1378 public int[] supplyPukReportResultForSubscriber(int subId, String puk, String pin) { 1379 enforceModifyPermission(); 1380 final UnlockSim checkSimPuk = new UnlockSim(getPhone(subId).getIccCard()); 1381 checkSimPuk.start(); 1382 return checkSimPuk.unlockSim(puk, pin); 1383 } 1384 1385 /** 1386 * Helper thread to turn async call to SimCard#supplyPin into 1387 * a synchronous one. 1388 */ 1389 private static class UnlockSim extends Thread { 1390 1391 private final IccCard mSimCard; 1392 1393 private boolean mDone = false; 1394 private int mResult = PhoneConstants.PIN_GENERAL_FAILURE; 1395 private int mRetryCount = -1; 1396 1397 // For replies from SimCard interface 1398 private Handler mHandler; 1399 1400 // For async handler to identify request type 1401 private static final int SUPPLY_PIN_COMPLETE = 100; 1402 1403 public UnlockSim(IccCard simCard) { 1404 mSimCard = simCard; 1405 } 1406 1407 @Override 1408 public void run() { 1409 Looper.prepare(); 1410 synchronized (UnlockSim.this) { 1411 mHandler = new Handler() { 1412 @Override 1413 public void handleMessage(Message msg) { 1414 AsyncResult ar = (AsyncResult) msg.obj; 1415 switch (msg.what) { 1416 case SUPPLY_PIN_COMPLETE: 1417 Log.d(LOG_TAG, "SUPPLY_PIN_COMPLETE"); 1418 synchronized (UnlockSim.this) { 1419 mRetryCount = msg.arg1; 1420 if (ar.exception != null) { 1421 if (ar.exception instanceof CommandException && 1422 ((CommandException)(ar.exception)).getCommandError() 1423 == CommandException.Error.PASSWORD_INCORRECT) { 1424 mResult = PhoneConstants.PIN_PASSWORD_INCORRECT; 1425 } else { 1426 mResult = PhoneConstants.PIN_GENERAL_FAILURE; 1427 } 1428 } else { 1429 mResult = PhoneConstants.PIN_RESULT_SUCCESS; 1430 } 1431 mDone = true; 1432 UnlockSim.this.notifyAll(); 1433 } 1434 break; 1435 } 1436 } 1437 }; 1438 UnlockSim.this.notifyAll(); 1439 } 1440 Looper.loop(); 1441 } 1442 1443 /* 1444 * Use PIN or PUK to unlock SIM card 1445 * 1446 * If PUK is null, unlock SIM card with PIN 1447 * 1448 * If PUK is not null, unlock SIM card with PUK and set PIN code 1449 */ 1450 synchronized int[] unlockSim(String puk, String pin) { 1451 1452 while (mHandler == null) { 1453 try { 1454 wait(); 1455 } catch (InterruptedException e) { 1456 Thread.currentThread().interrupt(); 1457 } 1458 } 1459 Message callback = Message.obtain(mHandler, SUPPLY_PIN_COMPLETE); 1460 1461 if (puk == null) { 1462 mSimCard.supplyPin(pin, callback); 1463 } else { 1464 mSimCard.supplyPuk(puk, pin, callback); 1465 } 1466 1467 while (!mDone) { 1468 try { 1469 Log.d(LOG_TAG, "wait for done"); 1470 wait(); 1471 } catch (InterruptedException e) { 1472 // Restore the interrupted status 1473 Thread.currentThread().interrupt(); 1474 } 1475 } 1476 Log.d(LOG_TAG, "done"); 1477 int[] resultArray = new int[2]; 1478 resultArray[0] = mResult; 1479 resultArray[1] = mRetryCount; 1480 return resultArray; 1481 } 1482 } 1483 1484 public void updateServiceLocation() { 1485 updateServiceLocationForSubscriber(getDefaultSubscription()); 1486 1487 } 1488 1489 public void updateServiceLocationForSubscriber(int subId) { 1490 // No permission check needed here: this call is harmless, and it's 1491 // needed for the ServiceState.requestStateUpdate() call (which is 1492 // already intentionally exposed to 3rd parties.) 1493 final Phone phone = getPhone(subId); 1494 if (phone != null) { 1495 phone.updateServiceLocation(); 1496 } 1497 } 1498 1499 @Override 1500 public boolean isRadioOn(String callingPackage) { 1501 return isRadioOnForSubscriber(getDefaultSubscription(), callingPackage); 1502 } 1503 1504 @Override 1505 public boolean isRadioOnForSubscriber(int subId, String callingPackage) { 1506 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1507 mApp, subId, callingPackage, "isRadioOnForSubscriber")) { 1508 return false; 1509 } 1510 return isRadioOnForSubscriber(subId); 1511 } 1512 1513 private boolean isRadioOnForSubscriber(int subId) { 1514 final Phone phone = getPhone(subId); 1515 if (phone != null) { 1516 return phone.getServiceState().getState() != ServiceState.STATE_POWER_OFF; 1517 } else { 1518 return false; 1519 } 1520 } 1521 1522 public void toggleRadioOnOff() { 1523 toggleRadioOnOffForSubscriber(getDefaultSubscription()); 1524 1525 } 1526 1527 public void toggleRadioOnOffForSubscriber(int subId) { 1528 enforceModifyPermission(); 1529 final Phone phone = getPhone(subId); 1530 if (phone != null) { 1531 phone.setRadioPower(!isRadioOnForSubscriber(subId)); 1532 } 1533 } 1534 1535 public boolean setRadio(boolean turnOn) { 1536 return setRadioForSubscriber(getDefaultSubscription(), turnOn); 1537 } 1538 1539 public boolean setRadioForSubscriber(int subId, boolean turnOn) { 1540 enforceModifyPermission(); 1541 final Phone phone = getPhone(subId); 1542 if (phone == null) { 1543 return false; 1544 } 1545 if ((phone.getServiceState().getState() != 1546 ServiceState.STATE_POWER_OFF) != turnOn) { 1547 toggleRadioOnOffForSubscriber(subId); 1548 } 1549 return true; 1550 } 1551 1552 public boolean needMobileRadioShutdown() { 1553 /* 1554 * If any of the Radios are available, it will need to be 1555 * shutdown. So return true if any Radio is available. 1556 */ 1557 for (int i = 0; i < TelephonyManager.getDefault().getPhoneCount(); i++) { 1558 Phone phone = PhoneFactory.getPhone(i); 1559 if (phone != null && phone.isRadioAvailable()) return true; 1560 } 1561 logv(TelephonyManager.getDefault().getPhoneCount() + " Phones are shutdown."); 1562 return false; 1563 } 1564 1565 public void shutdownMobileRadios() { 1566 for (int i = 0; i < TelephonyManager.getDefault().getPhoneCount(); i++) { 1567 logv("Shutting down Phone " + i); 1568 shutdownRadioUsingPhoneId(i); 1569 } 1570 } 1571 1572 private void shutdownRadioUsingPhoneId(int phoneId) { 1573 enforceModifyPermission(); 1574 Phone phone = PhoneFactory.getPhone(phoneId); 1575 if (phone != null && phone.isRadioAvailable()) { 1576 phone.shutdownRadio(); 1577 } 1578 } 1579 1580 public boolean setRadioPower(boolean turnOn) { 1581 enforceModifyPermission(); 1582 final Phone defaultPhone = PhoneFactory.getDefaultPhone(); 1583 if (defaultPhone != null) { 1584 defaultPhone.setRadioPower(turnOn); 1585 return true; 1586 } else { 1587 loge("There's no default phone."); 1588 return false; 1589 } 1590 } 1591 1592 public boolean setRadioPowerForSubscriber(int subId, boolean turnOn) { 1593 enforceModifyPermission(); 1594 final Phone phone = getPhone(subId); 1595 if (phone != null) { 1596 phone.setRadioPower(turnOn); 1597 return true; 1598 } else { 1599 return false; 1600 } 1601 } 1602 1603 // FIXME: subId version needed 1604 @Override 1605 public boolean enableDataConnectivity() { 1606 enforceModifyPermission(); 1607 int subId = mSubscriptionController.getDefaultDataSubId(); 1608 final Phone phone = getPhone(subId); 1609 if (phone != null) { 1610 phone.setUserDataEnabled(true); 1611 return true; 1612 } else { 1613 return false; 1614 } 1615 } 1616 1617 // FIXME: subId version needed 1618 @Override 1619 public boolean disableDataConnectivity() { 1620 enforceModifyPermission(); 1621 int subId = mSubscriptionController.getDefaultDataSubId(); 1622 final Phone phone = getPhone(subId); 1623 if (phone != null) { 1624 phone.setUserDataEnabled(false); 1625 return true; 1626 } else { 1627 return false; 1628 } 1629 } 1630 1631 @Override 1632 public boolean isDataConnectivityPossible(int subId) { 1633 final Phone phone = getPhone(subId); 1634 if (phone != null) { 1635 return phone.isDataAllowed(); 1636 } else { 1637 return false; 1638 } 1639 } 1640 1641 public boolean handlePinMmi(String dialString) { 1642 return handlePinMmiForSubscriber(getDefaultSubscription(), dialString); 1643 } 1644 1645 public void handleUssdRequest(int subId, String ussdRequest, ResultReceiver wrappedCallback) { 1646 enforceCallPermission(); 1647 if (!SubscriptionManager.isValidSubscriptionId(subId)) { 1648 return; 1649 } 1650 Pair<String, ResultReceiver> ussdObject = new Pair(ussdRequest, wrappedCallback); 1651 sendRequest(CMD_HANDLE_USSD_REQUEST, ussdObject, subId); 1652 }; 1653 1654 public boolean handlePinMmiForSubscriber(int subId, String dialString) { 1655 enforceModifyPermission(); 1656 if (!SubscriptionManager.isValidSubscriptionId(subId)) { 1657 return false; 1658 } 1659 return (Boolean) sendRequest(CMD_HANDLE_PIN_MMI, dialString, subId); 1660 } 1661 1662 public int getCallState() { 1663 return getCallStateForSlot(getSlotForDefaultSubscription()); 1664 } 1665 1666 public int getCallStateForSlot(int slotIndex) { 1667 Phone phone = PhoneFactory.getPhone(slotIndex); 1668 return phone == null ? TelephonyManager.CALL_STATE_IDLE : 1669 PhoneConstantConversions.convertCallState(phone.getState()); 1670 } 1671 1672 @Override 1673 public int getDataState() { 1674 Phone phone = getPhone(mSubscriptionController.getDefaultDataSubId()); 1675 if (phone != null) { 1676 return PhoneConstantConversions.convertDataState(phone.getDataConnectionState()); 1677 } else { 1678 return PhoneConstantConversions.convertDataState(PhoneConstants.DataState.DISCONNECTED); 1679 } 1680 } 1681 1682 @Override 1683 public int getDataActivity() { 1684 Phone phone = getPhone(mSubscriptionController.getDefaultDataSubId()); 1685 if (phone != null) { 1686 return DefaultPhoneNotifier.convertDataActivityState(phone.getDataActivityState()); 1687 } else { 1688 return TelephonyManager.DATA_ACTIVITY_NONE; 1689 } 1690 } 1691 1692 @Override 1693 public Bundle getCellLocation(String callingPackage) { 1694 mPhone.getContext().getSystemService(AppOpsManager.class) 1695 .checkPackage(Binder.getCallingUid(), callingPackage); 1696 if (!LocationAccessPolicy.canAccessCellLocation(mPhone.getContext(), 1697 callingPackage, Binder.getCallingUid(), Binder.getCallingPid(), true)) { 1698 return null; 1699 } 1700 1701 if (DBG_LOC) log("getCellLocation: is active user"); 1702 Bundle data = new Bundle(); 1703 Phone phone = getPhone(mSubscriptionController.getDefaultDataSubId()); 1704 if (phone == null) { 1705 return null; 1706 } 1707 1708 WorkSource workSource = getWorkSource(Binder.getCallingUid()); 1709 phone.getCellLocation(workSource).fillInNotifierBundle(data); 1710 return data; 1711 } 1712 1713 @Override 1714 public String getNetworkCountryIsoForPhone(int phoneId) { 1715 // Reporting the correct network country is ambiguous when IWLAN could conflict with 1716 // registered cell info, so return a NULL country instead. 1717 final long identity = Binder.clearCallingIdentity(); 1718 try { 1719 final int subId = mSubscriptionController.getSubIdUsingPhoneId(phoneId); 1720 // Todo: fix this when we can get the actual cellular network info when the device 1721 // is on IWLAN. 1722 if (TelephonyManager.NETWORK_TYPE_IWLAN 1723 == getVoiceNetworkTypeForSubscriber(subId, mApp.getPackageName())) { 1724 return ""; 1725 } 1726 } finally { 1727 Binder.restoreCallingIdentity(identity); 1728 } 1729 1730 Phone phone = PhoneFactory.getPhone(phoneId); 1731 if (phone != null) { 1732 ServiceStateTracker sst = phone.getServiceStateTracker(); 1733 if (sst != null) { 1734 LocaleTracker lt = sst.getLocaleTracker(); 1735 if (lt != null) { 1736 return lt.getCurrentCountry(); 1737 } 1738 } 1739 } 1740 return ""; 1741 } 1742 1743 @Override 1744 public void enableLocationUpdates() { 1745 enableLocationUpdatesForSubscriber(getDefaultSubscription()); 1746 } 1747 1748 @Override 1749 public void enableLocationUpdatesForSubscriber(int subId) { 1750 mApp.enforceCallingOrSelfPermission( 1751 android.Manifest.permission.CONTROL_LOCATION_UPDATES, null); 1752 final Phone phone = getPhone(subId); 1753 if (phone != null) { 1754 phone.enableLocationUpdates(); 1755 } 1756 } 1757 1758 @Override 1759 public void disableLocationUpdates() { 1760 disableLocationUpdatesForSubscriber(getDefaultSubscription()); 1761 } 1762 1763 @Override 1764 public void disableLocationUpdatesForSubscriber(int subId) { 1765 mApp.enforceCallingOrSelfPermission( 1766 android.Manifest.permission.CONTROL_LOCATION_UPDATES, null); 1767 final Phone phone = getPhone(subId); 1768 if (phone != null) { 1769 phone.disableLocationUpdates(); 1770 } 1771 } 1772 1773 @Override 1774 @SuppressWarnings("unchecked") 1775 public List<NeighboringCellInfo> getNeighboringCellInfo(String callingPackage) { 1776 mPhone.getContext().getSystemService(AppOpsManager.class) 1777 .checkPackage(Binder.getCallingUid(), callingPackage); 1778 if (!LocationAccessPolicy.canAccessCellLocation(mPhone.getContext(), 1779 callingPackage, Binder.getCallingUid(), Binder.getCallingPid(), true)) { 1780 return null; 1781 } 1782 1783 if (mAppOps.noteOp(AppOpsManager.OP_NEIGHBORING_CELLS, Binder.getCallingUid(), 1784 callingPackage) != AppOpsManager.MODE_ALLOWED) { 1785 return null; 1786 } 1787 1788 if (DBG_LOC) log("getNeighboringCellInfo: is active user"); 1789 1790 ArrayList<NeighboringCellInfo> cells = null; 1791 1792 WorkSource workSource = getWorkSource(Binder.getCallingUid()); 1793 try { 1794 cells = (ArrayList<NeighboringCellInfo>) sendRequest( 1795 CMD_HANDLE_NEIGHBORING_CELL, workSource, 1796 SubscriptionManager.INVALID_SUBSCRIPTION_ID); 1797 } catch (RuntimeException e) { 1798 Log.e(LOG_TAG, "getNeighboringCellInfo " + e); 1799 } 1800 return cells; 1801 } 1802 1803 1804 @Override 1805 public List<CellInfo> getAllCellInfo(String callingPackage) { 1806 mPhone.getContext().getSystemService(AppOpsManager.class) 1807 .checkPackage(Binder.getCallingUid(), callingPackage); 1808 if (!LocationAccessPolicy.canAccessCellLocation(mPhone.getContext(), 1809 callingPackage, Binder.getCallingUid(), Binder.getCallingPid(), true)) { 1810 return null; 1811 } 1812 1813 if (DBG_LOC) log("getAllCellInfo: is active user"); 1814 WorkSource workSource = getWorkSource(Binder.getCallingUid()); 1815 List<CellInfo> cellInfos = new ArrayList<CellInfo>(); 1816 for (Phone phone : PhoneFactory.getPhones()) { 1817 final List<CellInfo> info = phone.getAllCellInfo(workSource); 1818 if (info != null) cellInfos.addAll(info); 1819 } 1820 return cellInfos; 1821 } 1822 1823 @Override 1824 public void setCellInfoListRate(int rateInMillis) { 1825 enforceModifyPermission(); 1826 WorkSource workSource = getWorkSource(Binder.getCallingUid()); 1827 mPhone.setCellInfoListRate(rateInMillis, workSource); 1828 } 1829 1830 @Override 1831 public String getImeiForSlot(int slotIndex, String callingPackage) { 1832 Phone phone = PhoneFactory.getPhone(slotIndex); 1833 if (phone == null) { 1834 return null; 1835 } 1836 int subId = phone.getSubId(); 1837 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1838 mApp, subId, callingPackage, "getImeiForSlot")) { 1839 return null; 1840 } 1841 return phone.getImei(); 1842 } 1843 1844 @Override 1845 public String getMeidForSlot(int slotIndex, String callingPackage) { 1846 Phone phone = PhoneFactory.getPhone(slotIndex); 1847 if (phone == null) { 1848 return null; 1849 } 1850 int subId = phone.getSubId(); 1851 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1852 mApp, subId, callingPackage, "getMeidForSlot")) { 1853 return null; 1854 } 1855 return phone.getMeid(); 1856 } 1857 1858 @Override 1859 public String getDeviceSoftwareVersionForSlot(int slotIndex, String callingPackage) { 1860 Phone phone = PhoneFactory.getPhone(slotIndex); 1861 if (phone == null) { 1862 return null; 1863 } 1864 int subId = phone.getSubId(); 1865 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1866 mApp, subId, callingPackage, "getDeviceSoftwareVersionForSlot")) { 1867 return null; 1868 } 1869 return phone.getDeviceSvn(); 1870 } 1871 1872 @Override 1873 public int getSubscriptionCarrierId(int subId) { 1874 final Phone phone = getPhone(subId); 1875 return phone == null ? TelephonyManager.UNKNOWN_CARRIER_ID : phone.getCarrierId(); 1876 } 1877 1878 @Override 1879 public String getSubscriptionCarrierName(int subId) { 1880 final Phone phone = getPhone(subId); 1881 return phone == null ? null : phone.getCarrierName(); 1882 } 1883 1884 // 1885 // Internal helper methods. 1886 // 1887 1888 /** 1889 * Make sure the caller has the MODIFY_PHONE_STATE permission. 1890 * 1891 * @throws SecurityException if the caller does not have the required permission 1892 */ 1893 private void enforceModifyPermission() { 1894 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.MODIFY_PHONE_STATE, null); 1895 } 1896 1897 /** 1898 * Make sure the caller has the CALL_PHONE permission. 1899 * 1900 * @throws SecurityException if the caller does not have the required permission 1901 */ 1902 private void enforceCallPermission() { 1903 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.CALL_PHONE, null); 1904 } 1905 1906 private void enforceConnectivityInternalPermission() { 1907 mApp.enforceCallingOrSelfPermission( 1908 android.Manifest.permission.CONNECTIVITY_INTERNAL, 1909 "ConnectivityService"); 1910 } 1911 1912 private String createTelUrl(String number) { 1913 if (TextUtils.isEmpty(number)) { 1914 return null; 1915 } 1916 1917 return "tel:" + number; 1918 } 1919 1920 private static void log(String msg) { 1921 Log.d(LOG_TAG, "[PhoneIntfMgr] " + msg); 1922 } 1923 1924 private static void logv(String msg) { 1925 Log.v(LOG_TAG, "[PhoneIntfMgr] " + msg); 1926 } 1927 1928 private static void loge(String msg) { 1929 Log.e(LOG_TAG, "[PhoneIntfMgr] " + msg); 1930 } 1931 1932 @Override 1933 public int getActivePhoneType() { 1934 return getActivePhoneTypeForSlot(getSlotForDefaultSubscription()); 1935 } 1936 1937 @Override 1938 public int getActivePhoneTypeForSlot(int slotIndex) { 1939 final Phone phone = PhoneFactory.getPhone(slotIndex); 1940 if (phone == null) { 1941 return PhoneConstants.PHONE_TYPE_NONE; 1942 } else { 1943 return phone.getPhoneType(); 1944 } 1945 } 1946 1947 /** 1948 * Returns the CDMA ERI icon index to display 1949 */ 1950 @Override 1951 public int getCdmaEriIconIndex(String callingPackage) { 1952 return getCdmaEriIconIndexForSubscriber(getDefaultSubscription(), callingPackage); 1953 } 1954 1955 @Override 1956 public int getCdmaEriIconIndexForSubscriber(int subId, String callingPackage) { 1957 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1958 mApp, subId, callingPackage, "getCdmaEriIconIndexForSubscriber")) { 1959 return -1; 1960 } 1961 final Phone phone = getPhone(subId); 1962 if (phone != null) { 1963 return phone.getCdmaEriIconIndex(); 1964 } else { 1965 return -1; 1966 } 1967 } 1968 1969 /** 1970 * Returns the CDMA ERI icon mode, 1971 * 0 - ON 1972 * 1 - FLASHING 1973 */ 1974 @Override 1975 public int getCdmaEriIconMode(String callingPackage) { 1976 return getCdmaEriIconModeForSubscriber(getDefaultSubscription(), callingPackage); 1977 } 1978 1979 @Override 1980 public int getCdmaEriIconModeForSubscriber(int subId, String callingPackage) { 1981 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 1982 mApp, subId, callingPackage, "getCdmaEriIconModeForSubscriber")) { 1983 return -1; 1984 } 1985 final Phone phone = getPhone(subId); 1986 if (phone != null) { 1987 return phone.getCdmaEriIconMode(); 1988 } else { 1989 return -1; 1990 } 1991 } 1992 1993 /** 1994 * Returns the CDMA ERI text, 1995 */ 1996 @Override 1997 public String getCdmaEriText(String callingPackage) { 1998 return getCdmaEriTextForSubscriber(getDefaultSubscription(), callingPackage); 1999 } 2000 2001 @Override 2002 public String getCdmaEriTextForSubscriber(int subId, String callingPackage) { 2003 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2004 mApp, subId, callingPackage, "getCdmaEriIconTextForSubscriber")) { 2005 return null; 2006 } 2007 final Phone phone = getPhone(subId); 2008 if (phone != null) { 2009 return phone.getCdmaEriText(); 2010 } else { 2011 return null; 2012 } 2013 } 2014 2015 /** 2016 * Returns the CDMA MDN. 2017 */ 2018 @Override 2019 public String getCdmaMdn(int subId) { 2020 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2021 mApp, subId, "getCdmaMdn"); 2022 final Phone phone = getPhone(subId); 2023 if (mPhone.getPhoneType() == PhoneConstants.PHONE_TYPE_CDMA && phone != null) { 2024 return phone.getLine1Number(); 2025 } else { 2026 return null; 2027 } 2028 } 2029 2030 /** 2031 * Returns the CDMA MIN. 2032 */ 2033 @Override 2034 public String getCdmaMin(int subId) { 2035 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2036 mApp, subId, "getCdmaMin"); 2037 final Phone phone = getPhone(subId); 2038 if (phone != null && phone.getPhoneType() == PhoneConstants.PHONE_TYPE_CDMA) { 2039 return phone.getCdmaMin(); 2040 } else { 2041 return null; 2042 } 2043 } 2044 2045 /** 2046 * Returns true if CDMA provisioning needs to run. 2047 */ 2048 public boolean needsOtaServiceProvisioning() { 2049 return mPhone.needsOtaServiceProvisioning(); 2050 } 2051 2052 /** 2053 * Sets the voice mail number of a given subId. 2054 */ 2055 @Override 2056 public boolean setVoiceMailNumber(int subId, String alphaTag, String number) { 2057 TelephonyPermissions.enforceCallingOrSelfCarrierPrivilege(subId, "setVoiceMailNumber"); 2058 Boolean success = (Boolean) sendRequest(CMD_SET_VOICEMAIL_NUMBER, 2059 new Pair<String, String>(alphaTag, number), new Integer(subId)); 2060 return success; 2061 } 2062 2063 @Override 2064 public Bundle getVisualVoicemailSettings(String callingPackage, int subId) { 2065 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2066 String systemDialer = TelecomManager.from(mPhone.getContext()).getSystemDialerPackage(); 2067 if (!TextUtils.equals(callingPackage, systemDialer)) { 2068 throw new SecurityException("caller must be system dialer"); 2069 } 2070 PhoneAccountHandle phoneAccountHandle = PhoneAccountHandleConverter.fromSubId(subId); 2071 if (phoneAccountHandle == null){ 2072 return null; 2073 } 2074 return VisualVoicemailSettingsUtil.dump(mPhone.getContext(), phoneAccountHandle); 2075 } 2076 2077 @Override 2078 public String getVisualVoicemailPackageName(String callingPackage, int subId) { 2079 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2080 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2081 mApp, subId, callingPackage, "getVisualVoicemailPackageName")) { 2082 return null; 2083 } 2084 final long identity = Binder.clearCallingIdentity(); 2085 try { 2086 return RemoteVvmTaskManager 2087 .getRemotePackage(mPhone.getContext(), subId).getPackageName(); 2088 } finally { 2089 Binder.restoreCallingIdentity(identity); 2090 } 2091 } 2092 2093 @Override 2094 public void enableVisualVoicemailSmsFilter(String callingPackage, int subId, 2095 VisualVoicemailSmsFilterSettings settings) { 2096 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2097 VisualVoicemailSmsFilterConfig 2098 .enableVisualVoicemailSmsFilter(mPhone.getContext(), callingPackage, subId, 2099 settings); 2100 } 2101 2102 @Override 2103 public void disableVisualVoicemailSmsFilter(String callingPackage, int subId) { 2104 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2105 VisualVoicemailSmsFilterConfig 2106 .disableVisualVoicemailSmsFilter(mPhone.getContext(), callingPackage, subId); 2107 } 2108 2109 @Override 2110 public VisualVoicemailSmsFilterSettings getVisualVoicemailSmsFilterSettings( 2111 String callingPackage, int subId) { 2112 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2113 return VisualVoicemailSmsFilterConfig 2114 .getVisualVoicemailSmsFilterSettings(mPhone.getContext(), callingPackage, subId); 2115 } 2116 2117 @Override 2118 public VisualVoicemailSmsFilterSettings getActiveVisualVoicemailSmsFilterSettings(int subId) { 2119 enforceReadPrivilegedPermission(); 2120 return VisualVoicemailSmsFilterConfig 2121 .getActiveVisualVoicemailSmsFilterSettings(mPhone.getContext(), subId); 2122 } 2123 2124 @Override 2125 public void sendVisualVoicemailSmsForSubscriber(String callingPackage, int subId, 2126 String number, int port, String text, PendingIntent sentIntent) { 2127 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2128 enforceVisualVoicemailPackage(callingPackage, subId); 2129 enforceSendSmsPermission(); 2130 // Make the calls as the phone process. 2131 final long identity = Binder.clearCallingIdentity(); 2132 try { 2133 SmsManager smsManager = SmsManager.getSmsManagerForSubscriptionId(subId); 2134 if (port == 0) { 2135 smsManager.sendTextMessageWithSelfPermissions(number, null, text, 2136 sentIntent, null, false); 2137 } else { 2138 byte[] data = text.getBytes(StandardCharsets.UTF_8); 2139 smsManager.sendDataMessageWithSelfPermissions(number, null, 2140 (short) port, data, sentIntent, null); 2141 } 2142 } finally { 2143 Binder.restoreCallingIdentity(identity); 2144 } 2145 } 2146 /** 2147 * Sets the voice activation state of a given subId. 2148 */ 2149 @Override 2150 public void setVoiceActivationState(int subId, int activationState) { 2151 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2152 mApp, subId, "setVoiceActivationState"); 2153 final Phone phone = getPhone(subId); 2154 if (phone != null) { 2155 phone.setVoiceActivationState(activationState); 2156 } else { 2157 loge("setVoiceActivationState fails with invalid subId: " + subId); 2158 } 2159 } 2160 2161 /** 2162 * Sets the data activation state of a given subId. 2163 */ 2164 @Override 2165 public void setDataActivationState(int subId, int activationState) { 2166 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2167 mApp, subId, "setDataActivationState"); 2168 final Phone phone = getPhone(subId); 2169 if (phone != null) { 2170 phone.setDataActivationState(activationState); 2171 } else { 2172 loge("setVoiceActivationState fails with invalid subId: " + subId); 2173 } 2174 } 2175 2176 /** 2177 * Returns the voice activation state of a given subId. 2178 */ 2179 @Override 2180 public int getVoiceActivationState(int subId, String callingPackage) { 2181 enforceReadPrivilegedPermission(); 2182 final Phone phone = getPhone(subId); 2183 if (phone != null) { 2184 return phone.getVoiceActivationState(); 2185 } else { 2186 return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN; 2187 } 2188 } 2189 2190 /** 2191 * Returns the data activation state of a given subId. 2192 */ 2193 @Override 2194 public int getDataActivationState(int subId, String callingPackage) { 2195 enforceReadPrivilegedPermission(); 2196 final Phone phone = getPhone(subId); 2197 if (phone != null) { 2198 return phone.getDataActivationState(); 2199 } else { 2200 return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN; 2201 } 2202 } 2203 2204 /** 2205 * Returns the unread count of voicemails 2206 */ 2207 public int getVoiceMessageCount() { 2208 return getVoiceMessageCountForSubscriber(getDefaultSubscription()); 2209 } 2210 2211 /** 2212 * Returns the unread count of voicemails for a subId 2213 */ 2214 @Override 2215 public int getVoiceMessageCountForSubscriber( int subId) { 2216 final Phone phone = getPhone(subId); 2217 if (phone != null) { 2218 return phone.getVoiceMessageCount(); 2219 } else { 2220 return 0; 2221 } 2222 } 2223 2224 /** 2225 * returns true, if the device is in a state where both voice and data 2226 * are supported simultaneously. This can change based on location or network condition. 2227 */ 2228 @Override 2229 public boolean isConcurrentVoiceAndDataAllowed(int subId) { 2230 final Phone phone = getPhone(subId); 2231 return (phone == null ? false : phone.isConcurrentVoiceAndDataAllowed()); 2232 } 2233 2234 /** 2235 * Send the dialer code if called from the current default dialer or the caller has 2236 * carrier privilege. 2237 * @param inputCode The dialer code to send 2238 */ 2239 @Override 2240 public void sendDialerSpecialCode(String callingPackage, String inputCode) { 2241 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2242 String defaultDialer = TelecomManager.from(mPhone.getContext()).getDefaultDialerPackage(); 2243 if (!TextUtils.equals(callingPackage, defaultDialer)) { 2244 TelephonyPermissions.enforceCallingOrSelfCarrierPrivilege( 2245 getDefaultSubscription(), "sendDialerSpecialCode"); 2246 } 2247 mPhone.sendDialerSpecialCode(inputCode); 2248 } 2249 2250 /** 2251 * Returns the data network type. 2252 * Legacy call, permission-free. 2253 * 2254 * @Deprecated to be removed Q3 2013 use {@link #getDataNetworkType}. 2255 */ 2256 @Override 2257 public int getNetworkType() { 2258 final Phone phone = getPhone(getDefaultSubscription()); 2259 if (phone != null) { 2260 return phone.getServiceState().getDataNetworkType(); 2261 } else { 2262 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2263 } 2264 } 2265 2266 /** 2267 * Returns the network type for a subId 2268 */ 2269 @Override 2270 public int getNetworkTypeForSubscriber(int subId, String callingPackage) { 2271 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2272 mApp, subId, callingPackage, "getNetworkTypeForSubscriber")) { 2273 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2274 } 2275 2276 final Phone phone = getPhone(subId); 2277 if (phone != null) { 2278 return phone.getServiceState().getDataNetworkType(); 2279 } else { 2280 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2281 } 2282 } 2283 2284 /** 2285 * Returns the data network type 2286 */ 2287 @Override 2288 public int getDataNetworkType(String callingPackage) { 2289 return getDataNetworkTypeForSubscriber(getDefaultSubscription(), callingPackage); 2290 } 2291 2292 /** 2293 * Returns the data network type for a subId 2294 */ 2295 @Override 2296 public int getDataNetworkTypeForSubscriber(int subId, String callingPackage) { 2297 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2298 mApp, subId, callingPackage, "getDataNetworkTypeForSubscriber")) { 2299 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2300 } 2301 2302 final Phone phone = getPhone(subId); 2303 if (phone != null) { 2304 return phone.getServiceState().getDataNetworkType(); 2305 } else { 2306 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2307 } 2308 } 2309 2310 /** 2311 * Returns the Voice network type for a subId 2312 */ 2313 @Override 2314 public int getVoiceNetworkTypeForSubscriber(int subId, String callingPackage) { 2315 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2316 mApp, subId, callingPackage, "getDataNetworkTypeForSubscriber")) { 2317 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2318 } 2319 2320 final Phone phone = getPhone(subId); 2321 if (phone != null) { 2322 return phone.getServiceState().getVoiceNetworkType(); 2323 } else { 2324 return TelephonyManager.NETWORK_TYPE_UNKNOWN; 2325 } 2326 } 2327 2328 /** 2329 * @return true if a ICC card is present 2330 */ 2331 public boolean hasIccCard() { 2332 // FIXME Make changes to pass defaultSimId of type int 2333 return hasIccCardUsingSlotIndex(mSubscriptionController.getSlotIndex( 2334 getDefaultSubscription())); 2335 } 2336 2337 /** 2338 * @return true if a ICC card is present for a slotIndex 2339 */ 2340 @Override 2341 public boolean hasIccCardUsingSlotIndex(int slotIndex) { 2342 final Phone phone = PhoneFactory.getPhone(slotIndex); 2343 if (phone != null) { 2344 return phone.getIccCard().hasIccCard(); 2345 } else { 2346 return false; 2347 } 2348 } 2349 2350 /** 2351 * Return if the current radio is LTE on CDMA. This 2352 * is a tri-state return value as for a period of time 2353 * the mode may be unknown. 2354 * 2355 * @param callingPackage the name of the package making the call. 2356 * @return {@link Phone#LTE_ON_CDMA_UNKNOWN}, {@link Phone#LTE_ON_CDMA_FALSE} 2357 * or {@link Phone#LTE_ON_CDMA_TRUE} 2358 */ 2359 @Override 2360 public int getLteOnCdmaMode(String callingPackage) { 2361 return getLteOnCdmaModeForSubscriber(getDefaultSubscription(), callingPackage); 2362 } 2363 2364 @Override 2365 public int getLteOnCdmaModeForSubscriber(int subId, String callingPackage) { 2366 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2367 mApp, subId, callingPackage, "getLteOnCdmaModeForSubscriber")) { 2368 return PhoneConstants.LTE_ON_CDMA_UNKNOWN; 2369 } 2370 2371 final Phone phone = getPhone(subId); 2372 if (phone == null) { 2373 return PhoneConstants.LTE_ON_CDMA_UNKNOWN; 2374 } else { 2375 return phone.getLteOnCdmaMode(); 2376 } 2377 } 2378 2379 public void setPhone(Phone phone) { 2380 mPhone = phone; 2381 } 2382 2383 /** 2384 * {@hide} 2385 * Returns Default subId, 0 in the case of single standby. 2386 */ 2387 private int getDefaultSubscription() { 2388 return mSubscriptionController.getDefaultSubId(); 2389 } 2390 2391 private int getSlotForDefaultSubscription() { 2392 return mSubscriptionController.getPhoneId(getDefaultSubscription()); 2393 } 2394 2395 private int getPreferredVoiceSubscription() { 2396 return mSubscriptionController.getDefaultVoiceSubId(); 2397 } 2398 2399 /** 2400 * @see android.telephony.TelephonyManager.WifiCallingChoices 2401 */ 2402 public int getWhenToMakeWifiCalls() { 2403 return Settings.System.getInt(mPhone.getContext().getContentResolver(), 2404 Settings.System.WHEN_TO_MAKE_WIFI_CALLS, getWhenToMakeWifiCallsDefaultPreference()); 2405 } 2406 2407 /** 2408 * @see android.telephony.TelephonyManager.WifiCallingChoices 2409 */ 2410 public void setWhenToMakeWifiCalls(int preference) { 2411 if (DBG) log("setWhenToMakeWifiCallsStr, storing setting = " + preference); 2412 Settings.System.putInt(mPhone.getContext().getContentResolver(), 2413 Settings.System.WHEN_TO_MAKE_WIFI_CALLS, preference); 2414 } 2415 2416 private static int getWhenToMakeWifiCallsDefaultPreference() { 2417 // TODO: Use a build property to choose this value. 2418 return TelephonyManager.WifiCallingChoices.ALWAYS_USE; 2419 } 2420 2421 @Override 2422 public IccOpenLogicalChannelResponse iccOpenLogicalChannel( 2423 int subId, String callingPackage, String aid, int p2) { 2424 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2425 mApp, subId, "iccOpenLogicalChannel"); 2426 2427 if (TextUtils.equals(ISDR_AID, aid)) { 2428 // Only allows LPA to open logical channel to ISD-R. 2429 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2430 ComponentInfo bestComponent = 2431 EuiccConnector.findBestComponent(mPhone.getContext().getPackageManager()); 2432 if (bestComponent == null 2433 || !TextUtils.equals(callingPackage, bestComponent.packageName)) { 2434 loge("The calling package is not allowed to access ISD-R."); 2435 throw new SecurityException("The calling package is not allowed to access ISD-R."); 2436 } 2437 } 2438 2439 if (DBG) log("iccOpenLogicalChannel: subId=" + subId + " aid=" + aid + " p2=" + p2); 2440 IccOpenLogicalChannelResponse response = (IccOpenLogicalChannelResponse)sendRequest( 2441 CMD_OPEN_CHANNEL, new Pair<String, Integer>(aid, p2), subId); 2442 if (DBG) log("iccOpenLogicalChannel: " + response); 2443 return response; 2444 } 2445 2446 @Override 2447 public boolean iccCloseLogicalChannel(int subId, int channel) { 2448 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2449 mApp, subId, "iccCloseLogicalChannel"); 2450 2451 if (DBG) log("iccCloseLogicalChannel: subId=" + subId + " chnl=" + channel); 2452 if (channel < 0) { 2453 return false; 2454 } 2455 Boolean success = (Boolean)sendRequest(CMD_CLOSE_CHANNEL, channel, subId); 2456 if (DBG) log("iccCloseLogicalChannel: " + success); 2457 return success; 2458 } 2459 2460 @Override 2461 public String iccTransmitApduLogicalChannel(int subId, int channel, int cla, 2462 int command, int p1, int p2, int p3, String data) { 2463 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2464 mApp, subId, "iccTransmitApduLogicalChannel"); 2465 2466 if (DBG) { 2467 log("iccTransmitApduLogicalChannel: subId=" + subId + " chnl=" + channel + 2468 " cla=" + cla + " cmd=" + command + " p1=" + p1 + " p2=" + p2 + " p3=" + p3 + 2469 " data=" + data); 2470 } 2471 2472 if (channel < 0) { 2473 return ""; 2474 } 2475 2476 IccIoResult response = (IccIoResult)sendRequest(CMD_TRANSMIT_APDU_LOGICAL_CHANNEL, 2477 new IccAPDUArgument(channel, cla, command, p1, p2, p3, data), subId); 2478 if (DBG) log("iccTransmitApduLogicalChannel: " + response); 2479 2480 // Append the returned status code to the end of the response payload. 2481 String s = Integer.toHexString( 2482 (response.sw1 << 8) + response.sw2 + 0x10000).substring(1); 2483 if (response.payload != null) { 2484 s = IccUtils.bytesToHexString(response.payload) + s; 2485 } 2486 return s; 2487 } 2488 2489 @Override 2490 public String iccTransmitApduBasicChannel(int subId, String callingPackage, int cla, 2491 int command, int p1, int p2, int p3, String data) { 2492 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2493 mApp, subId, "iccTransmitApduBasicChannel"); 2494 2495 if (command == SELECT_COMMAND && p1 == SELECT_P1 && p2 == SELECT_P2 && p3 == SELECT_P3 2496 && TextUtils.equals(ISDR_AID, data)) { 2497 // Only allows LPA to select ISD-R. 2498 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 2499 ComponentInfo bestComponent = 2500 EuiccConnector.findBestComponent(mPhone.getContext().getPackageManager()); 2501 if (bestComponent == null 2502 || !TextUtils.equals(callingPackage, bestComponent.packageName)) { 2503 loge("The calling package is not allowed to select ISD-R."); 2504 throw new SecurityException("The calling package is not allowed to select ISD-R."); 2505 } 2506 } 2507 2508 if (DBG) { 2509 log("iccTransmitApduBasicChannel: subId=" + subId + " cla=" + cla + " cmd=" + command 2510 + " p1=" + p1 + " p2=" + p2 + " p3=" + p3 + " data=" + data); 2511 } 2512 2513 IccIoResult response = (IccIoResult)sendRequest(CMD_TRANSMIT_APDU_BASIC_CHANNEL, 2514 new IccAPDUArgument(0, cla, command, p1, p2, p3, data), subId); 2515 if (DBG) log("iccTransmitApduBasicChannel: " + response); 2516 2517 // Append the returned status code to the end of the response payload. 2518 String s = Integer.toHexString( 2519 (response.sw1 << 8) + response.sw2 + 0x10000).substring(1); 2520 if (response.payload != null) { 2521 s = IccUtils.bytesToHexString(response.payload) + s; 2522 } 2523 return s; 2524 } 2525 2526 @Override 2527 public byte[] iccExchangeSimIO(int subId, int fileID, int command, int p1, int p2, int p3, 2528 String filePath) { 2529 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2530 mApp, subId, "iccExchangeSimIO"); 2531 2532 if (DBG) { 2533 log("Exchange SIM_IO " + subId + ":" + fileID + ":" + command + " " + 2534 p1 + " " + p2 + " " + p3 + ":" + filePath); 2535 } 2536 2537 IccIoResult response = 2538 (IccIoResult)sendRequest(CMD_EXCHANGE_SIM_IO, 2539 new IccAPDUArgument(-1, fileID, command, p1, p2, p3, filePath), 2540 subId); 2541 2542 if (DBG) { 2543 log("Exchange SIM_IO [R]" + response); 2544 } 2545 2546 byte[] result = null; 2547 int length = 2; 2548 if (response.payload != null) { 2549 length = 2 + response.payload.length; 2550 result = new byte[length]; 2551 System.arraycopy(response.payload, 0, result, 0, response.payload.length); 2552 } else { 2553 result = new byte[length]; 2554 } 2555 2556 result[length - 1] = (byte) response.sw2; 2557 result[length - 2] = (byte) response.sw1; 2558 return result; 2559 } 2560 2561 /** 2562 * Get the forbidden PLMN List from the given app type (ex APPTYPE_USIM) 2563 * on a particular subscription 2564 */ 2565 public String[] getForbiddenPlmns(int subId, int appType, String callingPackage) { 2566 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2567 mApp, subId, callingPackage, "getForbiddenPlmns")) { 2568 return null; 2569 } 2570 if (appType != TelephonyManager.APPTYPE_USIM && appType != TelephonyManager.APPTYPE_SIM) { 2571 loge("getForbiddenPlmnList(): App Type must be USIM or SIM"); 2572 return null; 2573 } 2574 Object response = sendRequest( 2575 CMD_GET_FORBIDDEN_PLMNS, new Integer(appType), subId); 2576 if (response instanceof String[]) { 2577 return (String[]) response; 2578 } 2579 // Response is an Exception of some kind, which is signalled to the user as a NULL retval 2580 return null; 2581 } 2582 2583 @Override 2584 public String sendEnvelopeWithStatus(int subId, String content) { 2585 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2586 mApp, subId, "sendEnvelopeWithStatus"); 2587 2588 IccIoResult response = (IccIoResult)sendRequest(CMD_SEND_ENVELOPE, content, subId); 2589 if (response.payload == null) { 2590 return ""; 2591 } 2592 2593 // Append the returned status code to the end of the response payload. 2594 String s = Integer.toHexString( 2595 (response.sw1 << 8) + response.sw2 + 0x10000).substring(1); 2596 s = IccUtils.bytesToHexString(response.payload) + s; 2597 return s; 2598 } 2599 2600 /** 2601 * Read one of the NV items defined in {@link com.android.internal.telephony.RadioNVItems} 2602 * and {@code ril_nv_items.h}. Used for device configuration by some CDMA operators. 2603 * 2604 * @param itemID the ID of the item to read 2605 * @return the NV item as a String, or null on error. 2606 */ 2607 @Override 2608 public String nvReadItem(int itemID) { 2609 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2610 mApp, getDefaultSubscription(), "nvReadItem"); 2611 if (DBG) log("nvReadItem: item " + itemID); 2612 String value = (String) sendRequest(CMD_NV_READ_ITEM, itemID); 2613 if (DBG) log("nvReadItem: item " + itemID + " is \"" + value + '"'); 2614 return value; 2615 } 2616 2617 /** 2618 * Write one of the NV items defined in {@link com.android.internal.telephony.RadioNVItems} 2619 * and {@code ril_nv_items.h}. Used for device configuration by some CDMA operators. 2620 * 2621 * @param itemID the ID of the item to read 2622 * @param itemValue the value to write, as a String 2623 * @return true on success; false on any failure 2624 */ 2625 @Override 2626 public boolean nvWriteItem(int itemID, String itemValue) { 2627 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2628 mApp, getDefaultSubscription(), "nvWriteItem"); 2629 if (DBG) log("nvWriteItem: item " + itemID + " value \"" + itemValue + '"'); 2630 Boolean success = (Boolean) sendRequest(CMD_NV_WRITE_ITEM, 2631 new Pair<Integer, String>(itemID, itemValue)); 2632 if (DBG) log("nvWriteItem: item " + itemID + ' ' + (success ? "ok" : "fail")); 2633 return success; 2634 } 2635 2636 /** 2637 * Update the CDMA Preferred Roaming List (PRL) in the radio NV storage. 2638 * Used for device configuration by some CDMA operators. 2639 * 2640 * @param preferredRoamingList byte array containing the new PRL 2641 * @return true on success; false on any failure 2642 */ 2643 @Override 2644 public boolean nvWriteCdmaPrl(byte[] preferredRoamingList) { 2645 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2646 mApp, getDefaultSubscription(), "nvWriteCdmaPrl"); 2647 if (DBG) log("nvWriteCdmaPrl: value: " + HexDump.toHexString(preferredRoamingList)); 2648 Boolean success = (Boolean) sendRequest(CMD_NV_WRITE_CDMA_PRL, preferredRoamingList); 2649 if (DBG) log("nvWriteCdmaPrl: " + (success ? "ok" : "fail")); 2650 return success; 2651 } 2652 2653 /** 2654 * Perform the specified type of NV config reset. 2655 * Used for device configuration by some CDMA operators. 2656 * 2657 * @param resetType the type of reset to perform (1 == factory reset; 2 == NV-only reset) 2658 * @return true on success; false on any failure 2659 */ 2660 @Override 2661 public boolean nvResetConfig(int resetType) { 2662 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2663 mApp, getDefaultSubscription(), "nvResetConfig"); 2664 if (DBG) log("nvResetConfig: type " + resetType); 2665 Boolean success = (Boolean) sendRequest(CMD_NV_RESET_CONFIG, resetType); 2666 if (DBG) log("nvResetConfig: type " + resetType + ' ' + (success ? "ok" : "fail")); 2667 return success; 2668 } 2669 2670 /** 2671 * {@hide} 2672 * Returns Default sim, 0 in the case of single standby. 2673 */ 2674 public int getDefaultSim() { 2675 //TODO Need to get it from Telephony Devcontroller 2676 return 0; 2677 } 2678 2679 public String[] getPcscfAddress(String apnType, String callingPackage) { 2680 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2681 mApp, mPhone.getSubId(), callingPackage, "getPcscfAddress")) { 2682 return new String[0]; 2683 } 2684 2685 2686 return mPhone.getPcscfAddress(apnType); 2687 } 2688 2689 /** 2690 * Enables IMS for the framework. This will trigger IMS registration and ImsFeature capability 2691 * status updates, if not already enabled. 2692 */ 2693 public void enableIms(int slotId) { 2694 enforceModifyPermission(); 2695 PhoneFactory.getImsResolver().enableIms(slotId); 2696 } 2697 2698 /** 2699 * Disables IMS for the framework. This will trigger IMS de-registration and trigger ImsFeature 2700 * status updates to disabled. 2701 */ 2702 public void disableIms(int slotId) { 2703 enforceModifyPermission(); 2704 PhoneFactory.getImsResolver().disableIms(slotId); 2705 } 2706 2707 /** 2708 * Returns the {@link IImsMmTelFeature} that corresponds to the given slot Id for the MMTel 2709 * feature or {@link null} if the service is not available. If the feature is available, the 2710 * {@link IImsServiceFeatureCallback} callback is registered as a listener for feature updates. 2711 */ 2712 public IImsMmTelFeature getMmTelFeatureAndListen(int slotId, 2713 IImsServiceFeatureCallback callback) { 2714 enforceModifyPermission(); 2715 return PhoneFactory.getImsResolver().getMmTelFeatureAndListen(slotId, callback); 2716 } 2717 2718 /** 2719 * Returns the {@link IImsRcsFeature} that corresponds to the given slot Id for the RCS 2720 * feature during emergency calling or {@link null} if the service is not available. If the 2721 * feature is available, the {@link IImsServiceFeatureCallback} callback is registered as a 2722 * listener for feature updates. 2723 */ 2724 public IImsRcsFeature getRcsFeatureAndListen(int slotId, IImsServiceFeatureCallback callback) { 2725 enforceModifyPermission(); 2726 return PhoneFactory.getImsResolver().getRcsFeatureAndListen(slotId, callback); 2727 } 2728 2729 /** 2730 * Returns the {@link IImsRegistration} structure associated with the slotId and feature 2731 * specified. 2732 */ 2733 public IImsRegistration getImsRegistration(int slotId, int feature) throws RemoteException { 2734 enforceModifyPermission(); 2735 return PhoneFactory.getImsResolver().getImsRegistration(slotId, feature); 2736 } 2737 2738 /** 2739 * Returns the {@link IImsConfig} structure associated with the slotId and feature 2740 * specified. 2741 */ 2742 public IImsConfig getImsConfig(int slotId, int feature) throws RemoteException { 2743 enforceModifyPermission(); 2744 return PhoneFactory.getImsResolver().getImsConfig(slotId, feature); 2745 } 2746 2747 /** 2748 * @return true if the IMS resolver is busy resolving a binding and should not be considered 2749 * available, false if the IMS resolver is idle. 2750 */ 2751 public boolean isResolvingImsBinding() { 2752 enforceModifyPermission(); 2753 return PhoneFactory.getImsResolver().isResolvingBinding(); 2754 } 2755 2756 /** 2757 * Sets the ImsService Package Name that Telephony will bind to. 2758 * 2759 * @param slotId the slot ID that the ImsService should bind for. 2760 * @param isCarrierImsService true if the ImsService is the carrier override, false if the 2761 * ImsService is the device default ImsService. 2762 * @param packageName The package name of the application that contains the ImsService to bind 2763 * to. 2764 * @return true if setting the ImsService to bind to succeeded, false if it did not. 2765 * @hide 2766 */ 2767 public boolean setImsService(int slotId, boolean isCarrierImsService, String packageName) { 2768 int[] subIds = SubscriptionManager.getSubId(slotId); 2769 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege(mApp, 2770 (subIds != null ? subIds[0] : SubscriptionManager.INVALID_SUBSCRIPTION_ID), 2771 "setImsService"); 2772 2773 return PhoneFactory.getImsResolver().overrideImsServiceConfiguration(slotId, 2774 isCarrierImsService, packageName); 2775 } 2776 2777 /** 2778 * Return the ImsService configuration. 2779 * 2780 * @param slotId The slot that the ImsService is associated with. 2781 * @param isCarrierImsService true, if the ImsService is a carrier override, false if it is 2782 * the device default. 2783 * @return the package name of the ImsService configuration. 2784 */ 2785 public String getImsService(int slotId, boolean isCarrierImsService) { 2786 int[] subIds = SubscriptionManager.getSubId(slotId); 2787 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege(mApp, 2788 (subIds != null ? subIds[0] : SubscriptionManager.INVALID_SUBSCRIPTION_ID), 2789 "getImsService"); 2790 2791 return PhoneFactory.getImsResolver().getImsServiceConfiguration(slotId, 2792 isCarrierImsService); 2793 } 2794 2795 public void setImsRegistrationState(boolean registered) { 2796 enforceModifyPermission(); 2797 mPhone.setImsRegistrationState(registered); 2798 } 2799 2800 /** 2801 * Set the network selection mode to automatic. 2802 * 2803 */ 2804 @Override 2805 public void setNetworkSelectionModeAutomatic(int subId) { 2806 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2807 mApp, subId, "setNetworkSelectionModeAutomatic"); 2808 if (DBG) log("setNetworkSelectionModeAutomatic: subId " + subId); 2809 sendRequest(CMD_SET_NETWORK_SELECTION_MODE_AUTOMATIC, null, subId); 2810 } 2811 2812 /** 2813 * Set the network selection mode to manual with the selected carrier. 2814 */ 2815 @Override 2816 public boolean setNetworkSelectionModeManual(int subId, String operatorNumeric, 2817 boolean persistSelection) { 2818 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2819 mApp, subId, "setNetworkSelectionModeManual"); 2820 OperatorInfo operator = new OperatorInfo( 2821 /* operatorAlphaLong */ "", 2822 /* operatorAlphaShort */ "", 2823 operatorNumeric); 2824 if (DBG) log("setNetworkSelectionModeManual: subId:" + subId + " operator:" + operator); 2825 ManualNetworkSelectionArgument arg = new ManualNetworkSelectionArgument(operator, 2826 persistSelection); 2827 return (Boolean) sendRequest(CMD_SET_NETWORK_SELECTION_MODE_MANUAL, arg, subId); 2828 } 2829 2830 /** 2831 * Scans for available networks. 2832 */ 2833 @Override 2834 public CellNetworkScanResult getCellNetworkScanResults(int subId) { 2835 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2836 mApp, subId, "getCellNetworkScanResults"); 2837 if (DBG) log("getCellNetworkScanResults: subId " + subId); 2838 CellNetworkScanResult result = (CellNetworkScanResult) sendRequest( 2839 CMD_PERFORM_NETWORK_SCAN, null, subId); 2840 return result; 2841 } 2842 2843 /** 2844 * Starts a new network scan and returns the id of this scan. 2845 * 2846 * @param subId id of the subscription 2847 * @param request contains the radio access networks with bands/channels to scan 2848 * @param messenger callback messenger for scan results or errors 2849 * @param binder for the purpose of auto clean when the user thread crashes 2850 * @return the id of the requested scan which can be used to stop the scan. 2851 */ 2852 @Override 2853 public int requestNetworkScan(int subId, NetworkScanRequest request, Messenger messenger, 2854 IBinder binder) { 2855 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2856 mApp, subId, "requestNetworkScan"); 2857 return mNetworkScanRequestTracker.startNetworkScan( 2858 request, messenger, binder, getPhone(subId)); 2859 } 2860 2861 /** 2862 * Stops an existing network scan with the given scanId. 2863 * 2864 * @param subId id of the subscription 2865 * @param scanId id of the scan that needs to be stopped 2866 */ 2867 @Override 2868 public void stopNetworkScan(int subId, int scanId) { 2869 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2870 mApp, subId, "stopNetworkScan"); 2871 mNetworkScanRequestTracker.stopNetworkScan(scanId); 2872 } 2873 2874 /** 2875 * Get the calculated preferred network type. 2876 * Used for debugging incorrect network type. 2877 * 2878 * @return the preferred network type, defined in RILConstants.java. 2879 */ 2880 @Override 2881 public int getCalculatedPreferredNetworkType(String callingPackage) { 2882 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 2883 mApp, mPhone.getSubId(), callingPackage, "getCalculatedPreferredNetworkType")) { 2884 return RILConstants.PREFERRED_NETWORK_MODE; 2885 } 2886 2887 return PhoneFactory.calculatePreferredNetworkType(mPhone.getContext(), 0); // wink FIXME: need to get SubId from somewhere. 2888 } 2889 2890 /** 2891 * Get the preferred network type. 2892 * Used for device configuration by some CDMA operators. 2893 * 2894 * @return the preferred network type, defined in RILConstants.java. 2895 */ 2896 @Override 2897 public int getPreferredNetworkType(int subId) { 2898 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2899 mApp, subId, "getPreferredNetworkType"); 2900 if (DBG) log("getPreferredNetworkType"); 2901 int[] result = (int[]) sendRequest(CMD_GET_PREFERRED_NETWORK_TYPE, null, subId); 2902 int networkType = (result != null ? result[0] : -1); 2903 if (DBG) log("getPreferredNetworkType: " + networkType); 2904 return networkType; 2905 } 2906 2907 /** 2908 * Set the preferred network type. 2909 * Used for device configuration by some CDMA operators. 2910 * 2911 * @param networkType the preferred network type, defined in RILConstants.java. 2912 * @return true on success; false on any failure. 2913 */ 2914 @Override 2915 public boolean setPreferredNetworkType(int subId, int networkType) { 2916 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2917 mApp, subId, "setPreferredNetworkType"); 2918 if (DBG) log("setPreferredNetworkType: subId " + subId + " type " + networkType); 2919 Boolean success = (Boolean) sendRequest(CMD_SET_PREFERRED_NETWORK_TYPE, networkType, subId); 2920 if (DBG) log("setPreferredNetworkType: " + (success ? "ok" : "fail")); 2921 if (success) { 2922 Settings.Global.putInt(mPhone.getContext().getContentResolver(), 2923 Settings.Global.PREFERRED_NETWORK_MODE + subId, networkType); 2924 } 2925 return success; 2926 } 2927 2928 /** 2929 * Check TETHER_DUN_REQUIRED and TETHER_DUN_APN settings, net.tethering.noprovisioning 2930 * SystemProperty, and config_tether_apndata to decide whether DUN APN is required for 2931 * tethering. 2932 * 2933 * @return 0: Not required. 1: required. 2: Not set. 2934 * @hide 2935 */ 2936 @Override 2937 public int getTetherApnRequired() { 2938 enforceModifyPermission(); 2939 int dunRequired = Settings.Global.getInt(mPhone.getContext().getContentResolver(), 2940 Settings.Global.TETHER_DUN_REQUIRED, 2); 2941 // If not set, check net.tethering.noprovisioning, TETHER_DUN_APN setting and 2942 // config_tether_apndata. 2943 if (dunRequired == 2 && mPhone.hasMatchedTetherApnSetting()) { 2944 dunRequired = 1; 2945 } 2946 return dunRequired; 2947 } 2948 2949 /** 2950 * Set mobile data enabled 2951 * Used by the user through settings etc to turn on/off mobile data 2952 * 2953 * @param enable {@code true} turn turn data on, else {@code false} 2954 */ 2955 @Override 2956 public void setUserDataEnabled(int subId, boolean enable) { 2957 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 2958 mApp, subId, "setUserDataEnabled"); 2959 int phoneId = mSubscriptionController.getPhoneId(subId); 2960 if (DBG) log("setUserDataEnabled: subId=" + subId + " phoneId=" + phoneId); 2961 Phone phone = PhoneFactory.getPhone(phoneId); 2962 if (phone != null) { 2963 if (DBG) log("setUserDataEnabled: subId=" + subId + " enable=" + enable); 2964 phone.setUserDataEnabled(enable); 2965 } else { 2966 loge("setUserDataEnabled: no phone for subId=" + subId); 2967 } 2968 } 2969 2970 /** 2971 * Get the user enabled state of Mobile Data. 2972 * 2973 * TODO: remove and use isUserDataEnabled. 2974 * This can't be removed now because some vendor codes 2975 * calls through ITelephony directly while they should 2976 * use TelephonyManager. 2977 * 2978 * @return true on enabled 2979 */ 2980 @Override 2981 public boolean getDataEnabled(int subId) { 2982 return isUserDataEnabled(subId); 2983 } 2984 2985 /** 2986 * Get whether mobile data is enabled per user setting. 2987 * 2988 * There are other factors deciding whether mobile data is actually enabled, but they are 2989 * not considered here. See {@link #isDataEnabled(int)} for more details. 2990 * 2991 * Accepts either ACCESS_NETWORK_STATE, MODIFY_PHONE_STATE or carrier privileges. 2992 * 2993 * @return {@code true} if data is enabled else {@code false} 2994 */ 2995 @Override 2996 public boolean isUserDataEnabled(int subId) { 2997 try { 2998 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.ACCESS_NETWORK_STATE, 2999 null); 3000 } catch (Exception e) { 3001 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 3002 mApp, subId, "isUserDataEnabled"); 3003 } 3004 int phoneId = mSubscriptionController.getPhoneId(subId); 3005 if (DBG) log("isUserDataEnabled: subId=" + subId + " phoneId=" + phoneId); 3006 Phone phone = PhoneFactory.getPhone(phoneId); 3007 if (phone != null) { 3008 boolean retVal = phone.isUserDataEnabled(); 3009 if (DBG) log("isUserDataEnabled: subId=" + subId + " retVal=" + retVal); 3010 return retVal; 3011 } else { 3012 if (DBG) loge("isUserDataEnabled: no phone subId=" + subId + " retVal=false"); 3013 return false; 3014 } 3015 } 3016 3017 /** 3018 * Get whether mobile data is enabled. 3019 * 3020 * Comparable to {@link #isUserDataEnabled(int)}, this considers all factors deciding 3021 * whether mobile data is actually enabled. 3022 * 3023 * Accepts either ACCESS_NETWORK_STATE, MODIFY_PHONE_STATE or carrier privileges. 3024 * 3025 * @return {@code true} if data is enabled else {@code false} 3026 */ 3027 @Override 3028 public boolean isDataEnabled(int subId) { 3029 try { 3030 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.ACCESS_NETWORK_STATE, 3031 null); 3032 } catch (Exception e) { 3033 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 3034 mApp, subId, "isDataEnabled"); 3035 } 3036 int phoneId = mSubscriptionController.getPhoneId(subId); 3037 if (DBG) log("isDataEnabled: subId=" + subId + " phoneId=" + phoneId); 3038 Phone phone = PhoneFactory.getPhone(phoneId); 3039 if (phone != null) { 3040 boolean retVal = phone.isDataEnabled(); 3041 if (DBG) log("isDataEnabled: subId=" + subId + " retVal=" + retVal); 3042 return retVal; 3043 } else { 3044 if (DBG) loge("isDataEnabled: no phone subId=" + subId + " retVal=false"); 3045 return false; 3046 } 3047 } 3048 3049 @Override 3050 public int getCarrierPrivilegeStatus(int subId) { 3051 final Phone phone = getPhone(subId); 3052 if (phone == null) { 3053 loge("getCarrierPrivilegeStatus: Invalid subId"); 3054 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_NO_ACCESS; 3055 } 3056 UiccCard card = UiccController.getInstance().getUiccCard(phone.getPhoneId()); 3057 if (card == null) { 3058 loge("getCarrierPrivilegeStatus: No UICC"); 3059 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_RULES_NOT_LOADED; 3060 } 3061 return card.getCarrierPrivilegeStatusForCurrentTransaction( 3062 phone.getContext().getPackageManager()); 3063 } 3064 3065 @Override 3066 public int getCarrierPrivilegeStatusForUid(int subId, int uid) { 3067 final Phone phone = getPhone(subId); 3068 if (phone == null) { 3069 loge("getCarrierPrivilegeStatus: Invalid subId"); 3070 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_NO_ACCESS; 3071 } 3072 UiccProfile profile = 3073 UiccController.getInstance().getUiccProfileForPhone(phone.getPhoneId()); 3074 if (profile == null) { 3075 loge("getCarrierPrivilegeStatus: No UICC"); 3076 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_RULES_NOT_LOADED; 3077 } 3078 return profile.getCarrierPrivilegeStatusForUid(phone.getContext().getPackageManager(), uid); 3079 } 3080 3081 @Override 3082 public int checkCarrierPrivilegesForPackage(String pkgName) { 3083 if (TextUtils.isEmpty(pkgName)) 3084 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_NO_ACCESS; 3085 UiccCard card = UiccController.getInstance().getUiccCard(mPhone.getPhoneId()); 3086 if (card == null) { 3087 loge("checkCarrierPrivilegesForPackage: No UICC"); 3088 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_RULES_NOT_LOADED; 3089 } 3090 return card.getCarrierPrivilegeStatus(mPhone.getContext().getPackageManager(), pkgName); 3091 } 3092 3093 @Override 3094 public int checkCarrierPrivilegesForPackageAnyPhone(String pkgName) { 3095 if (TextUtils.isEmpty(pkgName)) 3096 return TelephonyManager.CARRIER_PRIVILEGE_STATUS_NO_ACCESS; 3097 int result = TelephonyManager.CARRIER_PRIVILEGE_STATUS_RULES_NOT_LOADED; 3098 for (int i = 0; i < TelephonyManager.getDefault().getPhoneCount(); i++) { 3099 UiccCard card = UiccController.getInstance().getUiccCard(i); 3100 if (card == null) { 3101 // No UICC in that slot. 3102 continue; 3103 } 3104 3105 result = card.getCarrierPrivilegeStatus( 3106 mPhone.getContext().getPackageManager(), pkgName); 3107 if (result == TelephonyManager.CARRIER_PRIVILEGE_STATUS_HAS_ACCESS) { 3108 break; 3109 } 3110 } 3111 3112 return result; 3113 } 3114 3115 @Override 3116 public List<String> getCarrierPackageNamesForIntentAndPhone(Intent intent, int phoneId) { 3117 if (!SubscriptionManager.isValidPhoneId(phoneId)) { 3118 loge("phoneId " + phoneId + " is not valid."); 3119 return null; 3120 } 3121 UiccCard card = UiccController.getInstance().getUiccCard(phoneId); 3122 if (card == null) { 3123 loge("getCarrierPackageNamesForIntent: No UICC"); 3124 return null ; 3125 } 3126 return card.getCarrierPackageNamesForIntent( 3127 mPhone.getContext().getPackageManager(), intent); 3128 } 3129 3130 @Override 3131 public List<String> getPackagesWithCarrierPrivileges() { 3132 PackageManager pm = mPhone.getContext().getPackageManager(); 3133 List<String> privilegedPackages = new ArrayList<>(); 3134 List<PackageInfo> packages = null; 3135 for (int i = 0; i < TelephonyManager.getDefault().getPhoneCount(); i++) { 3136 UiccCard card = UiccController.getInstance().getUiccCard(i); 3137 if (card == null) { 3138 // No UICC in that slot. 3139 continue; 3140 } 3141 if (card.hasCarrierPrivilegeRules()) { 3142 if (packages == null) { 3143 // Only check packages in user 0 for now 3144 packages = pm.getInstalledPackagesAsUser( 3145 PackageManager.MATCH_DISABLED_COMPONENTS 3146 | PackageManager.MATCH_DISABLED_UNTIL_USED_COMPONENTS 3147 | PackageManager.GET_SIGNATURES, UserHandle.USER_SYSTEM); 3148 } 3149 for (int p = packages.size() - 1; p >= 0; p--) { 3150 PackageInfo pkgInfo = packages.get(p); 3151 if (pkgInfo != null && pkgInfo.packageName != null 3152 && card.getCarrierPrivilegeStatus(pkgInfo) 3153 == TelephonyManager.CARRIER_PRIVILEGE_STATUS_HAS_ACCESS) { 3154 privilegedPackages.add(pkgInfo.packageName); 3155 } 3156 } 3157 } 3158 } 3159 return privilegedPackages; 3160 } 3161 3162 private String getIccId(int subId) { 3163 final Phone phone = getPhone(subId); 3164 UiccCard card = phone == null ? null : phone.getUiccCard(); 3165 if (card == null) { 3166 loge("getIccId: No UICC"); 3167 return null; 3168 } 3169 String iccId = card.getIccId(); 3170 if (TextUtils.isEmpty(iccId)) { 3171 loge("getIccId: ICC ID is null or empty."); 3172 return null; 3173 } 3174 return iccId; 3175 } 3176 3177 @Override 3178 public boolean setLine1NumberForDisplayForSubscriber(int subId, String alphaTag, 3179 String number) { 3180 TelephonyPermissions.enforceCallingOrSelfCarrierPrivilege( 3181 subId, "setLine1NumberForDisplayForSubscriber"); 3182 3183 final String iccId = getIccId(subId); 3184 final Phone phone = getPhone(subId); 3185 if (phone == null) { 3186 return false; 3187 } 3188 final String subscriberId = phone.getSubscriberId(); 3189 3190 if (DBG_MERGE) { 3191 Slog.d(LOG_TAG, "Setting line number for ICC=" + iccId + ", subscriberId=" 3192 + subscriberId + " to " + number); 3193 } 3194 3195 if (TextUtils.isEmpty(iccId)) { 3196 return false; 3197 } 3198 3199 final SharedPreferences.Editor editor = mTelephonySharedPreferences.edit(); 3200 3201 final String alphaTagPrefKey = PREF_CARRIERS_ALPHATAG_PREFIX + iccId; 3202 if (alphaTag == null) { 3203 editor.remove(alphaTagPrefKey); 3204 } else { 3205 editor.putString(alphaTagPrefKey, alphaTag); 3206 } 3207 3208 // Record both the line number and IMSI for this ICCID, since we need to 3209 // track all merged IMSIs based on line number 3210 final String numberPrefKey = PREF_CARRIERS_NUMBER_PREFIX + iccId; 3211 final String subscriberPrefKey = PREF_CARRIERS_SUBSCRIBER_PREFIX + iccId; 3212 if (number == null) { 3213 editor.remove(numberPrefKey); 3214 editor.remove(subscriberPrefKey); 3215 } else { 3216 editor.putString(numberPrefKey, number); 3217 editor.putString(subscriberPrefKey, subscriberId); 3218 } 3219 3220 editor.commit(); 3221 return true; 3222 } 3223 3224 @Override 3225 public String getLine1NumberForDisplay(int subId, String callingPackage) { 3226 // This is open to apps with WRITE_SMS. 3227 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneNumber( 3228 mApp, subId, callingPackage, "getLine1NumberForDisplay")) { 3229 if (DBG_MERGE) log("getLine1NumberForDisplay returning null due to permission"); 3230 return null; 3231 } 3232 3233 String iccId = getIccId(subId); 3234 if (iccId != null) { 3235 String numberPrefKey = PREF_CARRIERS_NUMBER_PREFIX + iccId; 3236 if (DBG_MERGE) { 3237 log("getLine1NumberForDisplay returning " + 3238 mTelephonySharedPreferences.getString(numberPrefKey, null)); 3239 } 3240 return mTelephonySharedPreferences.getString(numberPrefKey, null); 3241 } 3242 if (DBG_MERGE) log("getLine1NumberForDisplay returning null as iccId is null"); 3243 return null; 3244 } 3245 3246 @Override 3247 public String getLine1AlphaTagForDisplay(int subId, String callingPackage) { 3248 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3249 mApp, subId, callingPackage, "getLine1AlphaTagForDisplay")) { 3250 return null; 3251 } 3252 3253 String iccId = getIccId(subId); 3254 if (iccId != null) { 3255 String alphaTagPrefKey = PREF_CARRIERS_ALPHATAG_PREFIX + iccId; 3256 return mTelephonySharedPreferences.getString(alphaTagPrefKey, null); 3257 } 3258 return null; 3259 } 3260 3261 @Override 3262 public String[] getMergedSubscriberIds(String callingPackage) { 3263 // This API isn't public, so no need to provide a valid subscription ID - we're not worried 3264 // about carrier-privileged callers not having access. 3265 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3266 mApp, SubscriptionManager.INVALID_SUBSCRIPTION_ID, callingPackage, 3267 "getMergedSubscriberIds")) { 3268 return null; 3269 } 3270 final Context context = mPhone.getContext(); 3271 final TelephonyManager tele = TelephonyManager.from(context); 3272 final SubscriptionManager sub = SubscriptionManager.from(context); 3273 3274 // Figure out what subscribers are currently active 3275 final ArraySet<String> activeSubscriberIds = new ArraySet<>(); 3276 // Clear calling identity, when calling TelephonyManager, because callerUid must be 3277 // the process, where TelephonyManager was instantiated. Otherwise AppOps check will fail. 3278 final long identity = Binder.clearCallingIdentity(); 3279 try { 3280 final int[] subIds = sub.getActiveSubscriptionIdList(); 3281 for (int subId : subIds) { 3282 activeSubscriberIds.add(tele.getSubscriberId(subId)); 3283 } 3284 } finally { 3285 Binder.restoreCallingIdentity(identity); 3286 } 3287 3288 // First pass, find a number override for an active subscriber 3289 String mergeNumber = null; 3290 final Map<String, ?> prefs = mTelephonySharedPreferences.getAll(); 3291 for (String key : prefs.keySet()) { 3292 if (key.startsWith(PREF_CARRIERS_SUBSCRIBER_PREFIX)) { 3293 final String subscriberId = (String) prefs.get(key); 3294 if (activeSubscriberIds.contains(subscriberId)) { 3295 final String iccId = key.substring(PREF_CARRIERS_SUBSCRIBER_PREFIX.length()); 3296 final String numberKey = PREF_CARRIERS_NUMBER_PREFIX + iccId; 3297 mergeNumber = (String) prefs.get(numberKey); 3298 if (DBG_MERGE) { 3299 Slog.d(LOG_TAG, "Found line number " + mergeNumber 3300 + " for active subscriber " + subscriberId); 3301 } 3302 if (!TextUtils.isEmpty(mergeNumber)) { 3303 break; 3304 } 3305 } 3306 } 3307 } 3308 3309 // Shortcut when no active merged subscribers 3310 if (TextUtils.isEmpty(mergeNumber)) { 3311 return null; 3312 } 3313 3314 // Second pass, find all subscribers under that line override 3315 final ArraySet<String> result = new ArraySet<>(); 3316 for (String key : prefs.keySet()) { 3317 if (key.startsWith(PREF_CARRIERS_NUMBER_PREFIX)) { 3318 final String number = (String) prefs.get(key); 3319 if (mergeNumber.equals(number)) { 3320 final String iccId = key.substring(PREF_CARRIERS_NUMBER_PREFIX.length()); 3321 final String subscriberKey = PREF_CARRIERS_SUBSCRIBER_PREFIX + iccId; 3322 final String subscriberId = (String) prefs.get(subscriberKey); 3323 if (!TextUtils.isEmpty(subscriberId)) { 3324 result.add(subscriberId); 3325 } 3326 } 3327 } 3328 } 3329 3330 final String[] resultArray = result.toArray(new String[result.size()]); 3331 Arrays.sort(resultArray); 3332 if (DBG_MERGE) { 3333 Slog.d(LOG_TAG, "Found subscribers " + Arrays.toString(resultArray) + " after merge"); 3334 } 3335 return resultArray; 3336 } 3337 3338 @Override 3339 public boolean setOperatorBrandOverride(int subId, String brand) { 3340 TelephonyPermissions.enforceCallingOrSelfCarrierPrivilege( 3341 subId, "setOperatorBrandOverride"); 3342 final Phone phone = getPhone(subId); 3343 return phone == null ? false : phone.setOperatorBrandOverride(brand); 3344 } 3345 3346 @Override 3347 public boolean setRoamingOverride(int subId, List<String> gsmRoamingList, 3348 List<String> gsmNonRoamingList, List<String> cdmaRoamingList, 3349 List<String> cdmaNonRoamingList) { 3350 TelephonyPermissions.enforceCallingOrSelfCarrierPrivilege(subId, "setRoamingOverride"); 3351 final Phone phone = getPhone(subId); 3352 if (phone == null) { 3353 return false; 3354 } 3355 return phone.setRoamingOverride(gsmRoamingList, gsmNonRoamingList, cdmaRoamingList, 3356 cdmaNonRoamingList); 3357 } 3358 3359 @Override 3360 @Deprecated 3361 public int invokeOemRilRequestRaw(byte[] oemReq, byte[] oemResp) { 3362 enforceModifyPermission(); 3363 3364 int returnValue = 0; 3365 try { 3366 AsyncResult result = (AsyncResult)sendRequest(CMD_INVOKE_OEM_RIL_REQUEST_RAW, oemReq); 3367 if(result.exception == null) { 3368 if (result.result != null) { 3369 byte[] responseData = (byte[])(result.result); 3370 if(responseData.length > oemResp.length) { 3371 Log.w(LOG_TAG, "Buffer to copy response too small: Response length is " + 3372 responseData.length + "bytes. Buffer Size is " + 3373 oemResp.length + "bytes."); 3374 } 3375 System.arraycopy(responseData, 0, oemResp, 0, responseData.length); 3376 returnValue = responseData.length; 3377 } 3378 } else { 3379 CommandException ex = (CommandException) result.exception; 3380 returnValue = ex.getCommandError().ordinal(); 3381 if(returnValue > 0) returnValue *= -1; 3382 } 3383 } catch (RuntimeException e) { 3384 Log.w(LOG_TAG, "sendOemRilRequestRaw: Runtime Exception"); 3385 returnValue = (CommandException.Error.GENERIC_FAILURE.ordinal()); 3386 if(returnValue > 0) returnValue *= -1; 3387 } 3388 3389 return returnValue; 3390 } 3391 3392 @Override 3393 public void setRadioCapability(RadioAccessFamily[] rafs) { 3394 try { 3395 ProxyController.getInstance().setRadioCapability(rafs); 3396 } catch (RuntimeException e) { 3397 Log.w(LOG_TAG, "setRadioCapability: Runtime Exception"); 3398 } 3399 } 3400 3401 @Override 3402 public int getRadioAccessFamily(int phoneId, String callingPackage) { 3403 Phone phone = PhoneFactory.getPhone(phoneId); 3404 if (phone == null) { 3405 return RadioAccessFamily.RAF_UNKNOWN; 3406 } 3407 int subId = phone.getSubId(); 3408 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3409 mApp, subId, callingPackage, "getRadioAccessFamily")) { 3410 return RadioAccessFamily.RAF_UNKNOWN; 3411 } 3412 3413 return ProxyController.getInstance().getRadioAccessFamily(phoneId); 3414 } 3415 3416 @Override 3417 public void enableVideoCalling(boolean enable) { 3418 enforceModifyPermission(); 3419 ImsManager.getInstance(mPhone.getContext(), mPhone.getPhoneId()).setVtSetting(enable); 3420 } 3421 3422 @Override 3423 public boolean isVideoCallingEnabled(String callingPackage) { 3424 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3425 mApp, mPhone.getSubId(), callingPackage, "isVideoCallingEnabled")) { 3426 return false; 3427 } 3428 3429 // Check the user preference and the system-level IMS setting. Even if the user has 3430 // enabled video calling, if IMS is disabled we aren't able to support video calling. 3431 // In the long run, we may instead need to check if there exists a connection service 3432 // which can support video calling. 3433 ImsManager imsManager = ImsManager.getInstance(mPhone.getContext(), mPhone.getPhoneId()); 3434 return imsManager.isVtEnabledByPlatform() 3435 && imsManager.isEnhanced4gLteModeSettingEnabledByUser() 3436 && imsManager.isVtEnabledByUser(); 3437 } 3438 3439 @Override 3440 public boolean canChangeDtmfToneLength() { 3441 return mApp.getCarrierConfig().getBoolean(CarrierConfigManager.KEY_DTMF_TYPE_ENABLED_BOOL); 3442 } 3443 3444 @Override 3445 public boolean isWorldPhone() { 3446 return mApp.getCarrierConfig().getBoolean(CarrierConfigManager.KEY_WORLD_PHONE_BOOL); 3447 } 3448 3449 @Override 3450 public boolean isTtyModeSupported() { 3451 TelecomManager telecomManager = TelecomManager.from(mPhone.getContext()); 3452 TelephonyManager telephonyManager = 3453 (TelephonyManager) mPhone.getContext().getSystemService(Context.TELEPHONY_SERVICE); 3454 return telecomManager.isTtySupported(); 3455 } 3456 3457 @Override 3458 public boolean isHearingAidCompatibilitySupported() { 3459 return mPhone.getContext().getResources().getBoolean(R.bool.hac_enabled); 3460 } 3461 3462 public boolean isRttSupported() { 3463 boolean isCarrierSupported = 3464 mApp.getCarrierConfig().getBoolean(CarrierConfigManager.KEY_RTT_SUPPORTED_BOOL); 3465 boolean isDeviceSupported = 3466 mPhone.getContext().getResources().getBoolean(R.bool.config_support_rtt); 3467 return isCarrierSupported && isDeviceSupported; 3468 } 3469 3470 public boolean isRttEnabled() { 3471 return isRttSupported() && Settings.Secure.getInt(mPhone.getContext().getContentResolver(), 3472 Settings.Secure.RTT_CALLING_MODE, 0) != 0; 3473 } 3474 3475 /** 3476 * Returns the unique device ID of phone, for example, the IMEI for 3477 * GSM and the MEID for CDMA phones. Return null if device ID is not available. 3478 * 3479 * <p>Requires Permission: 3480 * {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE} 3481 */ 3482 @Override 3483 public String getDeviceId(String callingPackage) { 3484 final Phone phone = PhoneFactory.getPhone(0); 3485 if (phone == null) { 3486 return null; 3487 } 3488 int subId = phone.getSubId(); 3489 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3490 mApp, subId, callingPackage, "getDeviceId")) { 3491 return null; 3492 } 3493 return phone.getDeviceId(); 3494 } 3495 3496 /** 3497 * {@hide} 3498 * Returns the IMS Registration Status on a particular subid 3499 * 3500 * @param subId 3501 */ 3502 public boolean isImsRegistered(int subId) { 3503 Phone phone = getPhone(subId); 3504 if (phone != null) { 3505 return phone.isImsRegistered(); 3506 } else { 3507 return false; 3508 } 3509 } 3510 3511 @Override 3512 public int getSubIdForPhoneAccount(PhoneAccount phoneAccount) { 3513 return PhoneUtils.getSubIdForPhoneAccount(phoneAccount); 3514 } 3515 3516 /** 3517 * @return the VoWiFi calling availability. 3518 */ 3519 public boolean isWifiCallingAvailable(int subId) { 3520 Phone phone = getPhone(subId); 3521 if (phone != null) { 3522 return phone.isWifiCallingEnabled(); 3523 } else { 3524 return false; 3525 } 3526 } 3527 3528 /** 3529 * @return the VoLTE availability. 3530 */ 3531 public boolean isVolteAvailable(int subId) { 3532 Phone phone = getPhone(subId); 3533 if (phone != null) { 3534 return phone.isVolteEnabled(); 3535 } else { 3536 return false; 3537 } 3538 } 3539 3540 /** 3541 * @return the VT calling availability. 3542 */ 3543 public boolean isVideoTelephonyAvailable(int subId) { 3544 Phone phone = getPhone(subId); 3545 if (phone != null) { 3546 return phone.isVideoEnabled(); 3547 } else { 3548 return false; 3549 } 3550 } 3551 3552 /** 3553 * @return the IMS registration technology for the MMTEL feature. Valid return values are 3554 * defined in {@link ImsRegistrationImplBase}. 3555 */ 3556 public @ImsRegistrationImplBase.ImsRegistrationTech int getImsRegTechnologyForMmTel(int subId) { 3557 Phone phone = getPhone(subId); 3558 if (phone != null) { 3559 return phone.getImsRegistrationTech(); 3560 } else { 3561 return ImsRegistrationImplBase.REGISTRATION_TECH_NONE; 3562 } 3563 } 3564 3565 @Override 3566 public void factoryReset(int subId) { 3567 enforceConnectivityInternalPermission(); 3568 if (mUserManager.hasUserRestriction(UserManager.DISALLOW_NETWORK_RESET)) { 3569 return; 3570 } 3571 3572 final long identity = Binder.clearCallingIdentity(); 3573 try { 3574 if (SubscriptionManager.isUsableSubIdValue(subId) && !mUserManager.hasUserRestriction( 3575 UserManager.DISALLOW_CONFIG_MOBILE_NETWORKS)) { 3576 setUserDataEnabled(subId, getDefaultDataEnabled()); 3577 setNetworkSelectionModeAutomatic(subId); 3578 setPreferredNetworkType(subId, getDefaultNetworkType(subId)); 3579 mPhone.setDataRoamingEnabled(getDefaultDataRoamingEnabled(subId)); 3580 CarrierInfoManager.deleteAllCarrierKeysForImsiEncryption(mPhone.getContext()); 3581 } 3582 } finally { 3583 Binder.restoreCallingIdentity(identity); 3584 } 3585 } 3586 3587 @Override 3588 public String getLocaleFromDefaultSim() { 3589 // We query all subscriptions instead of just the active ones, because 3590 // this might be called early on in the provisioning flow when the 3591 // subscriptions potentially aren't active yet. 3592 final List<SubscriptionInfo> slist = getAllSubscriptionInfoList(); 3593 if (slist == null || slist.isEmpty()) { 3594 return null; 3595 } 3596 3597 // This function may be called very early, say, from the setup wizard, at 3598 // which point we won't have a default subscription set. If that's the case 3599 // we just choose the first, which will be valid in "most cases". 3600 final int defaultSubId = getDefaultSubscription(); 3601 SubscriptionInfo info = null; 3602 if (defaultSubId == SubscriptionManager.INVALID_SUBSCRIPTION_ID) { 3603 info = slist.get(0); 3604 } else { 3605 for (SubscriptionInfo item : slist) { 3606 if (item.getSubscriptionId() == defaultSubId) { 3607 info = item; 3608 break; 3609 } 3610 } 3611 3612 if (info == null) { 3613 return null; 3614 } 3615 } 3616 3617 // Try and fetch the locale from the carrier properties or from the SIM language 3618 // preferences (EF-PL and EF-LI)... 3619 final int mcc = info.getMcc(); 3620 final Phone defaultPhone = getPhone(info.getSubscriptionId()); 3621 String simLanguage = null; 3622 if (defaultPhone != null) { 3623 final Locale localeFromDefaultSim = defaultPhone.getLocaleFromSimAndCarrierPrefs(); 3624 if (localeFromDefaultSim != null) { 3625 if (!localeFromDefaultSim.getCountry().isEmpty()) { 3626 if (DBG) log("Using locale from default SIM:" + localeFromDefaultSim); 3627 return localeFromDefaultSim.toLanguageTag(); 3628 } else { 3629 simLanguage = localeFromDefaultSim.getLanguage(); 3630 } 3631 } 3632 } 3633 3634 // The SIM language preferences only store a language (e.g. fr = French), not an 3635 // exact locale (e.g. fr_FR = French/France). So, if the locale returned from 3636 // the SIM and carrier preferences does not include a country we add the country 3637 // determined from the SIM MCC to provide an exact locale. 3638 final Locale mccLocale = MccTable.getLocaleFromMcc(mPhone.getContext(), mcc, simLanguage); 3639 if (mccLocale != null) { 3640 if (DBG) log("No locale from default SIM, using mcc locale:" + mccLocale); 3641 return mccLocale.toLanguageTag(); 3642 } 3643 3644 if (DBG) log("No locale found - returning null"); 3645 return null; 3646 } 3647 3648 private List<SubscriptionInfo> getAllSubscriptionInfoList() { 3649 final long identity = Binder.clearCallingIdentity(); 3650 try { 3651 return mSubscriptionController.getAllSubInfoList( 3652 mPhone.getContext().getOpPackageName()); 3653 } finally { 3654 Binder.restoreCallingIdentity(identity); 3655 } 3656 } 3657 3658 private List<SubscriptionInfo> getActiveSubscriptionInfoList() { 3659 final long identity = Binder.clearCallingIdentity(); 3660 try { 3661 return mSubscriptionController.getActiveSubscriptionInfoList( 3662 mPhone.getContext().getOpPackageName()); 3663 } finally { 3664 Binder.restoreCallingIdentity(identity); 3665 } 3666 } 3667 3668 private final ModemActivityInfo mLastModemActivityInfo = 3669 new ModemActivityInfo(0, 0, 0, new int[0], 0, 0); 3670 3671 /** 3672 * Responds to the ResultReceiver with the {@link android.telephony.ModemActivityInfo} object 3673 * representing the state of the modem. 3674 * 3675 * NOTE: The underlying implementation clears the modem state, so there should only ever be one 3676 * caller to it. Everyone should call this class to get cumulative data. 3677 * @hide 3678 */ 3679 @Override 3680 public void requestModemActivityInfo(ResultReceiver result) { 3681 enforceModifyPermission(); 3682 ModemActivityInfo ret = null; 3683 synchronized (mLastModemActivityInfo) { 3684 ModemActivityInfo info = (ModemActivityInfo) sendRequest(CMD_GET_MODEM_ACTIVITY_INFO, 3685 null); 3686 if (info != null) { 3687 int[] mergedTxTimeMs = new int[ModemActivityInfo.TX_POWER_LEVELS]; 3688 for (int i = 0; i < mergedTxTimeMs.length; i++) { 3689 mergedTxTimeMs[i] = 3690 info.getTxTimeMillis()[i] + mLastModemActivityInfo.getTxTimeMillis()[i]; 3691 } 3692 mLastModemActivityInfo.setTimestamp(info.getTimestamp()); 3693 mLastModemActivityInfo.setSleepTimeMillis( 3694 info.getSleepTimeMillis() + mLastModemActivityInfo.getSleepTimeMillis()); 3695 mLastModemActivityInfo.setIdleTimeMillis( 3696 info.getIdleTimeMillis() + mLastModemActivityInfo.getIdleTimeMillis()); 3697 mLastModemActivityInfo.setTxTimeMillis(mergedTxTimeMs); 3698 mLastModemActivityInfo.setRxTimeMillis( 3699 info.getRxTimeMillis() + mLastModemActivityInfo.getRxTimeMillis()); 3700 mLastModemActivityInfo.setEnergyUsed( 3701 info.getEnergyUsed() + mLastModemActivityInfo.getEnergyUsed()); 3702 } 3703 ret = new ModemActivityInfo(mLastModemActivityInfo.getTimestamp(), 3704 mLastModemActivityInfo.getSleepTimeMillis(), 3705 mLastModemActivityInfo.getIdleTimeMillis(), 3706 mLastModemActivityInfo.getTxTimeMillis(), 3707 mLastModemActivityInfo.getRxTimeMillis(), 3708 mLastModemActivityInfo.getEnergyUsed()); 3709 } 3710 Bundle bundle = new Bundle(); 3711 bundle.putParcelable(TelephonyManager.MODEM_ACTIVITY_RESULT_KEY, ret); 3712 result.send(0, bundle); 3713 } 3714 3715 /** 3716 * {@hide} 3717 * Returns the service state information on specified subscription. 3718 */ 3719 @Override 3720 public ServiceState getServiceStateForSubscriber(int subId, String callingPackage) { 3721 3722 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 3723 mApp, subId, callingPackage, "getServiceStateForSubscriber")) { 3724 return null; 3725 } 3726 3727 final Phone phone = getPhone(subId); 3728 if (phone == null) { 3729 return null; 3730 } 3731 3732 return phone.getServiceState(); 3733 } 3734 3735 /** 3736 * Returns the URI for the per-account voicemail ringtone set in Phone settings. 3737 * 3738 * @param accountHandle The handle for the {@link PhoneAccount} for which to retrieve the 3739 * voicemail ringtone. 3740 * @return The URI for the ringtone to play when receiving a voicemail from a specific 3741 * PhoneAccount. 3742 */ 3743 @Override 3744 public Uri getVoicemailRingtoneUri(PhoneAccountHandle accountHandle) { 3745 Phone phone = PhoneUtils.getPhoneForPhoneAccountHandle(accountHandle); 3746 if (phone == null) { 3747 phone = mPhone; 3748 } 3749 3750 return VoicemailNotificationSettingsUtil.getRingtoneUri(phone.getContext()); 3751 } 3752 3753 /** 3754 * Sets the per-account voicemail ringtone. 3755 * 3756 * <p>Requires that the calling app is the default dialer, or has carrier privileges, or 3757 * has permission {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}. 3758 * 3759 * @param phoneAccountHandle The handle for the {@link PhoneAccount} for which to set the 3760 * voicemail ringtone. 3761 * @param uri The URI for the ringtone to play when receiving a voicemail from a specific 3762 * PhoneAccount. 3763 */ 3764 @Override 3765 public void setVoicemailRingtoneUri(String callingPackage, 3766 PhoneAccountHandle phoneAccountHandle, Uri uri) { 3767 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 3768 if (!TextUtils.equals(callingPackage, 3769 TelecomManager.from(mPhone.getContext()).getDefaultDialerPackage())) { 3770 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 3771 mApp, PhoneUtils.getSubIdForPhoneAccountHandle(phoneAccountHandle), 3772 "setVoicemailRingtoneUri"); 3773 } 3774 Phone phone = PhoneUtils.getPhoneForPhoneAccountHandle(phoneAccountHandle); 3775 if (phone == null){ 3776 phone = mPhone; 3777 } 3778 VoicemailNotificationSettingsUtil.setRingtoneUri(phone.getContext(), uri); 3779 } 3780 3781 /** 3782 * Returns whether vibration is set for voicemail notification in Phone settings. 3783 * 3784 * @param accountHandle The handle for the {@link PhoneAccount} for which to retrieve the 3785 * voicemail vibration setting. 3786 * @return {@code true} if the vibration is set for this PhoneAccount, {@code false} otherwise. 3787 */ 3788 @Override 3789 public boolean isVoicemailVibrationEnabled(PhoneAccountHandle accountHandle) { 3790 Phone phone = PhoneUtils.getPhoneForPhoneAccountHandle(accountHandle); 3791 if (phone == null) { 3792 phone = mPhone; 3793 } 3794 3795 return VoicemailNotificationSettingsUtil.isVibrationEnabled(phone.getContext()); 3796 } 3797 3798 /** 3799 * Sets the per-account voicemail vibration. 3800 * 3801 * <p>Requires that the calling app is the default dialer, or has carrier privileges, or 3802 * has permission {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}. 3803 * 3804 * @param phoneAccountHandle The handle for the {@link PhoneAccount} for which to set the 3805 * voicemail vibration setting. 3806 * @param enabled Whether to enable or disable vibration for voicemail notifications from a 3807 * specific PhoneAccount. 3808 */ 3809 @Override 3810 public void setVoicemailVibrationEnabled(String callingPackage, 3811 PhoneAccountHandle phoneAccountHandle, boolean enabled) { 3812 mAppOps.checkPackage(Binder.getCallingUid(), callingPackage); 3813 if (!TextUtils.equals(callingPackage, 3814 TelecomManager.from(mPhone.getContext()).getDefaultDialerPackage())) { 3815 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 3816 mApp, PhoneUtils.getSubIdForPhoneAccountHandle(phoneAccountHandle), 3817 "setVoicemailVibrationEnabled"); 3818 } 3819 3820 Phone phone = PhoneUtils.getPhoneForPhoneAccountHandle(phoneAccountHandle); 3821 if (phone == null){ 3822 phone = mPhone; 3823 } 3824 VoicemailNotificationSettingsUtil.setVibrationEnabled(phone.getContext(), enabled); 3825 } 3826 3827 /** 3828 * Make sure either called from same process as self (phone) or IPC caller has read privilege. 3829 * 3830 * @throws SecurityException if the caller does not have the required permission 3831 */ 3832 private void enforceReadPrivilegedPermission() { 3833 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE, 3834 null); 3835 } 3836 3837 /** 3838 * Make sure either called from same process as self (phone) or IPC caller has send SMS 3839 * permission. 3840 * 3841 * @throws SecurityException if the caller does not have the required permission 3842 */ 3843 private void enforceSendSmsPermission() { 3844 mApp.enforceCallingOrSelfPermission(permission.SEND_SMS, null); 3845 } 3846 3847 /** 3848 * Make sure called from the package in charge of visual voicemail. 3849 * 3850 * @throws SecurityException if the caller is not the visual voicemail package. 3851 */ 3852 private void enforceVisualVoicemailPackage(String callingPackage, int subId) { 3853 ComponentName componentName = 3854 RemoteVvmTaskManager.getRemotePackage(mPhone.getContext(), subId); 3855 if(componentName == null) { 3856 throw new SecurityException("Caller not current active visual voicemail package[null]"); 3857 } 3858 String vvmPackage = componentName.getPackageName(); 3859 if (!callingPackage.equals(vvmPackage)) { 3860 throw new SecurityException("Caller not current active visual voicemail package[" + 3861 vvmPackage + "]"); 3862 } 3863 } 3864 3865 /** 3866 * Return the application ID for the app type. 3867 * 3868 * @param subId the subscription ID that this request applies to. 3869 * @param appType the uicc app type. 3870 * @return Application ID for specificied app type, or null if no uicc. 3871 */ 3872 @Override 3873 public String getAidForAppType(int subId, int appType) { 3874 enforceReadPrivilegedPermission(); 3875 Phone phone = getPhone(subId); 3876 if (phone == null) { 3877 return null; 3878 } 3879 String aid = null; 3880 try { 3881 aid = UiccController.getInstance().getUiccCard(phone.getPhoneId()) 3882 .getApplicationByType(appType).getAid(); 3883 } catch (Exception e) { 3884 Log.e(LOG_TAG, "Not getting aid. Exception ex=" + e); 3885 } 3886 return aid; 3887 } 3888 3889 /** 3890 * Return the Electronic Serial Number. 3891 * 3892 * @param subId the subscription ID that this request applies to. 3893 * @return ESN or null if error. 3894 */ 3895 @Override 3896 public String getEsn(int subId) { 3897 enforceReadPrivilegedPermission(); 3898 Phone phone = getPhone(subId); 3899 if (phone == null) { 3900 return null; 3901 } 3902 String esn = null; 3903 try { 3904 esn = phone.getEsn(); 3905 } catch (Exception e) { 3906 Log.e(LOG_TAG, "Not getting ESN. Exception ex=" + e); 3907 } 3908 return esn; 3909 } 3910 3911 /** 3912 * Return the Preferred Roaming List Version. 3913 * 3914 * @param subId the subscription ID that this request applies to. 3915 * @return PRLVersion or null if error. 3916 */ 3917 @Override 3918 public String getCdmaPrlVersion(int subId) { 3919 enforceReadPrivilegedPermission(); 3920 Phone phone = getPhone(subId); 3921 if (phone == null) { 3922 return null; 3923 } 3924 String cdmaPrlVersion = null; 3925 try { 3926 cdmaPrlVersion = phone.getCdmaPrlVersion(); 3927 } catch (Exception e) { 3928 Log.e(LOG_TAG, "Not getting PRLVersion", e); 3929 } 3930 return cdmaPrlVersion; 3931 } 3932 3933 /** 3934 * Get snapshot of Telephony histograms 3935 * @return List of Telephony histograms 3936 * @hide 3937 */ 3938 @Override 3939 public List<TelephonyHistogram> getTelephonyHistograms() { 3940 TelephonyPermissions.enforceCallingOrSelfModifyPermissionOrCarrierPrivilege( 3941 mApp, getDefaultSubscription(), "getTelephonyHistograms"); 3942 return RIL.getTelephonyRILTimingHistograms(); 3943 } 3944 3945 /** 3946 * {@hide} 3947 * Set the allowed carrier list for slotIndex 3948 * Require system privileges. In the future we may add this to carrier APIs. 3949 * 3950 * @return The number of carriers set successfully, should match length of carriers 3951 */ 3952 @Override 3953 public int setAllowedCarriers(int slotIndex, List<CarrierIdentifier> carriers) { 3954 enforceModifyPermission(); 3955 3956 if (carriers == null) { 3957 throw new NullPointerException("carriers cannot be null"); 3958 } 3959 3960 int subId = SubscriptionManager.getSubId(slotIndex)[0]; 3961 int[] retVal = (int[]) sendRequest(CMD_SET_ALLOWED_CARRIERS, carriers, subId); 3962 return retVal[0]; 3963 } 3964 3965 /** 3966 * {@hide} 3967 * Get the allowed carrier list for slotIndex. 3968 * Require system privileges. In the future we may add this to carrier APIs. 3969 * 3970 * @return List of {@link android.service.telephony.CarrierIdentifier}; empty list 3971 * means all carriers are allowed. 3972 */ 3973 @Override 3974 public List<CarrierIdentifier> getAllowedCarriers(int slotIndex) { 3975 enforceReadPrivilegedPermission(); 3976 int subId = SubscriptionManager.getSubId(slotIndex)[0]; 3977 return (List<CarrierIdentifier>) sendRequest(CMD_GET_ALLOWED_CARRIERS, null, subId); 3978 } 3979 3980 /** 3981 * Action set from carrier signalling broadcast receivers to enable/disable metered apns 3982 * @param subId the subscription ID that this action applies to. 3983 * @param enabled control enable or disable metered apns. 3984 * {@hide} 3985 */ 3986 @Override 3987 public void carrierActionSetMeteredApnsEnabled(int subId, boolean enabled) { 3988 enforceModifyPermission(); 3989 final Phone phone = getPhone(subId); 3990 if (phone == null) { 3991 loge("carrierAction: SetMeteredApnsEnabled fails with invalid subId: " + subId); 3992 return; 3993 } 3994 try { 3995 phone.carrierActionSetMeteredApnsEnabled(enabled); 3996 } catch (Exception e) { 3997 Log.e(LOG_TAG, "carrierAction: SetMeteredApnsEnabled fails. Exception ex=" + e); 3998 } 3999 } 4000 4001 /** 4002 * Action set from carrier signalling broadcast receivers to enable/disable radio 4003 * @param subId the subscription ID that this action applies to. 4004 * @param enabled control enable or disable radio. 4005 * {@hide} 4006 */ 4007 @Override 4008 public void carrierActionSetRadioEnabled(int subId, boolean enabled) { 4009 enforceModifyPermission(); 4010 final Phone phone = getPhone(subId); 4011 if (phone == null) { 4012 loge("carrierAction: SetRadioEnabled fails with invalid sibId: " + subId); 4013 return; 4014 } 4015 try { 4016 phone.carrierActionSetRadioEnabled(enabled); 4017 } catch (Exception e) { 4018 Log.e(LOG_TAG, "carrierAction: SetRadioEnabled fails. Exception ex=" + e); 4019 } 4020 } 4021 4022 /** 4023 * Action set from carrier signalling broadcast receivers to start/stop reporting the default 4024 * network status based on which carrier apps could apply actions accordingly, 4025 * enable/disable default url handler for example. 4026 * 4027 * @param subId the subscription ID that this action applies to. 4028 * @param report control start/stop reporting the default network status. 4029 * {@hide} 4030 */ 4031 @Override 4032 public void carrierActionReportDefaultNetworkStatus(int subId, boolean report) { 4033 enforceModifyPermission(); 4034 final Phone phone = getPhone(subId); 4035 if (phone == null) { 4036 loge("carrierAction: ReportDefaultNetworkStatus fails with invalid sibId: " + subId); 4037 return; 4038 } 4039 try { 4040 phone.carrierActionReportDefaultNetworkStatus(report); 4041 } catch (Exception e) { 4042 Log.e(LOG_TAG, "carrierAction: ReportDefaultNetworkStatus fails. Exception ex=" + e); 4043 } 4044 } 4045 4046 /** 4047 * Called when "adb shell dumpsys phone" is invoked. Dump is also automatically invoked when a 4048 * bug report is being generated. 4049 */ 4050 @Override 4051 protected void dump(FileDescriptor fd, PrintWriter writer, String[] args) { 4052 if (mPhone.getContext().checkCallingOrSelfPermission(android.Manifest.permission.DUMP) 4053 != PackageManager.PERMISSION_GRANTED) { 4054 writer.println("Permission Denial: can't dump Phone from pid=" 4055 + Binder.getCallingPid() 4056 + ", uid=" + Binder.getCallingUid() 4057 + "without permission " 4058 + android.Manifest.permission.DUMP); 4059 return; 4060 } 4061 DumpsysHandler.dump(mPhone.getContext(), fd, writer, args); 4062 } 4063 4064 @Override 4065 public void onShellCommand(FileDescriptor in, FileDescriptor out, FileDescriptor err, 4066 String[] args, ShellCallback callback, ResultReceiver resultReceiver) 4067 throws RemoteException { 4068 (new TelephonyShellCommand(this)).exec(this, in, out, err, args, callback, resultReceiver); 4069 } 4070 4071 /** 4072 * Get aggregated video call data usage since boot. 4073 * 4074 * @param perUidStats True if requesting data usage per uid, otherwise overall usage. 4075 * @return Snapshot of video call data usage 4076 * {@hide} 4077 */ 4078 @Override 4079 public NetworkStats getVtDataUsage(int subId, boolean perUidStats) { 4080 mApp.enforceCallingOrSelfPermission(android.Manifest.permission.READ_NETWORK_USAGE_HISTORY, 4081 null); 4082 4083 // NetworkStatsService keeps tracking the active network interface and identity. It 4084 // records the delta with the corresponding network identity. We just return the total video 4085 // call data usage snapshot since boot. 4086 Phone phone = getPhone(subId); 4087 if (phone != null) { 4088 return phone.getVtDataUsage(perUidStats); 4089 } 4090 return null; 4091 } 4092 4093 /** 4094 * Policy control of data connection. Usually used when data limit is passed. 4095 * @param enabled True if enabling the data, otherwise disabling. 4096 * @param subId Subscription index 4097 * {@hide} 4098 */ 4099 @Override 4100 public void setPolicyDataEnabled(boolean enabled, int subId) { 4101 enforceModifyPermission(); 4102 Phone phone = getPhone(subId); 4103 if (phone != null) { 4104 phone.setPolicyDataEnabled(enabled); 4105 } 4106 } 4107 4108 /** 4109 * Get Client request stats 4110 * @return List of Client Request Stats 4111 * @hide 4112 */ 4113 @Override 4114 public List<ClientRequestStats> getClientRequestStats(String callingPackage, int subId) { 4115 if (!TelephonyPermissions.checkCallingOrSelfReadPhoneState( 4116 mApp, subId, callingPackage, "getClientRequestStats")) { 4117 return null; 4118 } 4119 4120 Phone phone = getPhone(subId); 4121 if (phone != null) { 4122 return phone.getClientRequestStats(); 4123 } 4124 4125 return null; 4126 } 4127 4128 private WorkSource getWorkSource(int uid) { 4129 String packageName = mPhone.getContext().getPackageManager().getNameForUid(uid); 4130 return new WorkSource(uid, packageName); 4131 } 4132 4133 /** 4134 * Set SIM card power state. 4135 * 4136 * @param slotIndex SIM slot id. 4137 * @param state State of SIM (power down, power up, pass through) 4138 * - {@link android.telephony.TelephonyManager#CARD_POWER_DOWN} 4139 * - {@link android.telephony.TelephonyManager#CARD_POWER_UP} 4140 * - {@link android.telephony.TelephonyManager#CARD_POWER_UP_PASS_THROUGH} 4141 * 4142 **/ 4143 @Override 4144 public void setSimPowerStateForSlot(int slotIndex, int state) { 4145 enforceModifyPermission(); 4146 Phone phone = PhoneFactory.getPhone(slotIndex); 4147 4148 if (phone != null) { 4149 phone.setSimPowerState(state); 4150 } 4151 } 4152 4153 private boolean isUssdApiAllowed(int subId) { 4154 CarrierConfigManager configManager = 4155 (CarrierConfigManager) mPhone.getContext().getSystemService( 4156 Context.CARRIER_CONFIG_SERVICE); 4157 if (configManager == null) { 4158 return false; 4159 } 4160 PersistableBundle pb = configManager.getConfigForSubId(subId); 4161 if (pb == null) { 4162 return false; 4163 } 4164 return pb.getBoolean( 4165 CarrierConfigManager.KEY_ALLOW_USSD_REQUESTS_VIA_TELEPHONY_MANAGER_BOOL); 4166 } 4167 4168 /** 4169 * Check if phone is in emergency callback mode 4170 * @return true if phone is in emergency callback mode 4171 * @param subId sub id 4172 */ 4173 @Override 4174 public boolean getEmergencyCallbackMode(int subId) { 4175 enforceReadPrivilegedPermission(); 4176 final Phone phone = getPhone(subId); 4177 if (phone != null) { 4178 return phone.isInEcm(); 4179 } else { 4180 return false; 4181 } 4182 } 4183 4184 /** 4185 * Get the current signal strength information for the given subscription. 4186 * Because this information is not updated when the device is in a low power state 4187 * it should not be relied-upon to be current. 4188 * @param subId Subscription index 4189 * @return the most recent cached signal strength info from the modem 4190 */ 4191 @Override 4192 public SignalStrength getSignalStrength(int subId) { 4193 Phone p = getPhone(subId); 4194 if (p == null) { 4195 return null; 4196 } 4197 4198 return p.getSignalStrength(); 4199 } 4200 4201 @Override 4202 public UiccSlotInfo[] getUiccSlotsInfo() { 4203 enforceReadPrivilegedPermission(); 4204 4205 UiccSlot[] slots = UiccController.getInstance().getUiccSlots(); 4206 if (slots == null) { 4207 Rlog.i(LOG_TAG, "slots is null."); 4208 return null; 4209 } 4210 4211 UiccSlotInfo[] infos = new UiccSlotInfo[slots.length]; 4212 for (int i = 0; i < slots.length; i++) { 4213 UiccSlot slot = slots[i]; 4214 if (slot == null) { 4215 continue; 4216 } 4217 4218 String cardId; 4219 UiccCard card = slot.getUiccCard(); 4220 if (card != null) { 4221 cardId = card.getCardId(); 4222 } else { 4223 cardId = slot.getIccId(); 4224 } 4225 4226 int cardState = 0; 4227 switch (slot.getCardState()) { 4228 case CARDSTATE_ABSENT: 4229 cardState = UiccSlotInfo.CARD_STATE_INFO_ABSENT; 4230 break; 4231 case CARDSTATE_PRESENT: 4232 cardState = UiccSlotInfo.CARD_STATE_INFO_PRESENT; 4233 break; 4234 case CARDSTATE_ERROR: 4235 cardState = UiccSlotInfo.CARD_STATE_INFO_ERROR; 4236 break; 4237 case CARDSTATE_RESTRICTED: 4238 cardState = UiccSlotInfo.CARD_STATE_INFO_RESTRICTED; 4239 break; 4240 default: 4241 break; 4242 4243 } 4244 4245 infos[i] = new UiccSlotInfo( 4246 slot.isActive(), 4247 slot.isEuicc(), 4248 cardId, 4249 cardState, 4250 slot.getPhoneId(), 4251 slot.isExtendedApduSupported()); 4252 } 4253 return infos; 4254 } 4255 4256 @Override 4257 public boolean switchSlots(int[] physicalSlots) { 4258 enforceModifyPermission(); 4259 return (Boolean) sendRequest(CMD_SWITCH_SLOTS, physicalSlots); 4260 } 4261 4262 @Override 4263 public void setRadioIndicationUpdateMode(int subId, int filters, int mode) { 4264 enforceModifyPermission(); 4265 final Phone phone = getPhone(subId); 4266 if (phone == null) { 4267 loge("setRadioIndicationUpdateMode fails with invalid subId: " + subId); 4268 return; 4269 } 4270 4271 phone.setRadioIndicationUpdateMode(filters, mode); 4272 } 4273 4274 /** 4275 * A test API to reload the UICC profile. 4276 * 4277 * <p>Requires that the calling app has permission 4278 * {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}. 4279 * @hide 4280 */ 4281 @Override 4282 public void refreshUiccProfile(int subId) { 4283 enforceModifyPermission(); 4284 4285 final long identity = Binder.clearCallingIdentity(); 4286 try { 4287 Phone phone = getPhone(subId); 4288 if (phone == null) { 4289 return; 4290 } 4291 UiccCard uiccCard = phone.getUiccCard(); 4292 if (uiccCard == null) { 4293 return; 4294 } 4295 UiccProfile uiccProfile = uiccCard.getUiccProfile(); 4296 if (uiccProfile == null) { 4297 return; 4298 } 4299 uiccProfile.refresh(); 4300 } finally { 4301 Binder.restoreCallingIdentity(identity); 4302 } 4303 } 4304 4305 /** 4306 * Returns false if the mobile data is disabled by default, otherwise return true. 4307 */ 4308 private boolean getDefaultDataEnabled() { 4309 return "true".equalsIgnoreCase( 4310 SystemProperties.get(DEFAULT_MOBILE_DATA_PROPERTY_NAME, "true")); 4311 } 4312 4313 /** 4314 * Returns true if the data roaming is enabled by default, i.e the system property 4315 * of {@link #DEFAULT_DATA_ROAMING_PROPERTY_NAME} is true or the config of 4316 * {@link CarrierConfigManager#KEY_CARRIER_DEFAULT_DATA_ROAMING_ENABLED_BOOL} is true. 4317 */ 4318 private boolean getDefaultDataRoamingEnabled(int subId) { 4319 final CarrierConfigManager configMgr = (CarrierConfigManager) 4320 mPhone.getContext().getSystemService(Context.CARRIER_CONFIG_SERVICE); 4321 boolean isDataRoamingEnabled = "true".equalsIgnoreCase( 4322 SystemProperties.get(DEFAULT_DATA_ROAMING_PROPERTY_NAME, "false")); 4323 isDataRoamingEnabled |= configMgr.getConfigForSubId(subId).getBoolean( 4324 CarrierConfigManager.KEY_CARRIER_DEFAULT_DATA_ROAMING_ENABLED_BOOL); 4325 return isDataRoamingEnabled; 4326 } 4327 4328 /** 4329 * Returns the default network type for the given {@code subId}, if the default network type is 4330 * not set, return {@link Phone#PREFERRED_NT_MODE}. 4331 */ 4332 private int getDefaultNetworkType(int subId) { 4333 return Integer.parseInt( 4334 TelephonyManager.getTelephonyProperty( 4335 mSubscriptionController.getPhoneId(subId), 4336 DEFAULT_NETWORK_MODE_PROPERTY_NAME, 4337 String.valueOf(Phone.PREFERRED_NT_MODE))); 4338 } 4339 4340 @Override 4341 public void setCarrierTestOverride(int subId, String mccmnc, String imsi, String iccid, String 4342 gid1, String gid2, String plmn, String spn) { 4343 enforceModifyPermission(); 4344 final Phone phone = getPhone(subId); 4345 if (phone == null) { 4346 loge("setCarrierTestOverride fails with invalid subId: " + subId); 4347 return; 4348 } 4349 phone.setCarrierTestOverride(mccmnc, imsi, iccid, gid1, gid2, plmn, spn); 4350 } 4351 4352 @Override 4353 public int getCarrierIdListVersion(int subId) { 4354 enforceReadPrivilegedPermission(); 4355 final Phone phone = getPhone(subId); 4356 if (phone == null) { 4357 loge("getCarrierIdListVersion fails with invalid subId: " + subId); 4358 return TelephonyManager.UNKNOWN_CARRIER_ID_LIST_VERSION; 4359 } 4360 return phone.getCarrierIdListVersion(); 4361 } 4362 } 4363