TelephonyManager.java revision 349f4eddf76d1f16966a7ae7b599e984f599cf2e
1/*
2 * Copyright (C) 2008 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
17package android.telephony;
18
19import android.annotation.Nullable;
20import android.annotation.SystemApi;
21import android.annotation.SdkConstant;
22import android.annotation.SdkConstant.SdkConstantType;
23import android.app.ActivityThread;
24import android.content.ContentResolver;
25import android.content.Context;
26import android.content.Intent;
27import android.net.ConnectivityManager;
28import android.net.Uri;
29import android.os.BatteryStats;
30import android.os.ResultReceiver;
31import android.provider.Settings;
32import android.provider.Settings.SettingNotFoundException;
33import android.os.Bundle;
34import android.os.RemoteException;
35import android.os.ServiceManager;
36import android.os.SystemProperties;
37import android.telecom.PhoneAccount;
38import android.telecom.PhoneAccountHandle;
39import android.util.Log;
40
41import com.android.internal.telecom.ITelecomService;
42import com.android.internal.telephony.CellNetworkScanResult;
43import com.android.internal.telephony.IPhoneSubInfo;
44import com.android.internal.telephony.ITelephony;
45import com.android.internal.telephony.ITelephonyRegistry;
46import com.android.internal.telephony.OperatorInfo;
47import com.android.internal.telephony.PhoneConstants;
48import com.android.internal.telephony.RILConstants;
49import com.android.internal.telephony.TelephonyProperties;
50
51import java.io.FileInputStream;
52import java.io.IOException;
53import java.util.Collections;
54import java.util.List;
55import java.util.regex.Matcher;
56import java.util.regex.Pattern;
57
58/**
59 * Provides access to information about the telephony services on
60 * the device. Applications can use the methods in this class to
61 * determine telephony services and states, as well as to access some
62 * types of subscriber information. Applications can also register
63 * a listener to receive notification of telephony state changes.
64 * <p>
65 * You do not instantiate this class directly; instead, you retrieve
66 * a reference to an instance through
67 * {@link android.content.Context#getSystemService
68 * Context.getSystemService(Context.TELEPHONY_SERVICE)}.
69 * <p>
70 * Note that access to some telephony information is
71 * permission-protected. Your application cannot access the protected
72 * information unless it has the appropriate permissions declared in
73 * its manifest file. Where permissions apply, they are noted in the
74 * the methods through which you access the protected information.
75 */
76public class TelephonyManager {
77    private static final String TAG = "TelephonyManager";
78
79    /**
80     * The key to use when placing the result of {@link #requestModemActivityInfo(ResultReceiver)}
81     * into the ResultReceiver Bundle.
82     * @hide
83     */
84    public static final String MODEM_ACTIVITY_RESULT_KEY =
85            BatteryStats.RESULT_RECEIVER_CONTROLLER_KEY;
86
87    private static ITelephonyRegistry sRegistry;
88
89    /**
90     * The allowed states of Wi-Fi calling.
91     *
92     * @hide
93     */
94    public interface WifiCallingChoices {
95        /** Always use Wi-Fi calling */
96        static final int ALWAYS_USE = 0;
97        /** Ask the user whether to use Wi-Fi on every call */
98        static final int ASK_EVERY_TIME = 1;
99        /** Never use Wi-Fi calling */
100        static final int NEVER_USE = 2;
101    }
102
103    private final Context mContext;
104    private SubscriptionManager mSubscriptionManager;
105
106    private static String multiSimConfig =
107            SystemProperties.get(TelephonyProperties.PROPERTY_MULTI_SIM_CONFIG);
108
109    /** Enum indicating multisim variants
110     *  DSDS - Dual SIM Dual Standby
111     *  DSDA - Dual SIM Dual Active
112     *  TSTS - Triple SIM Triple Standby
113     **/
114    /** @hide */
115    public enum MultiSimVariants {
116        DSDS,
117        DSDA,
118        TSTS,
119        UNKNOWN
120    };
121
122    /** @hide */
123    public TelephonyManager(Context context) {
124        Context appContext = context.getApplicationContext();
125        if (appContext != null) {
126            mContext = appContext;
127        } else {
128            mContext = context;
129        }
130        mSubscriptionManager = SubscriptionManager.from(mContext);
131
132        if (sRegistry == null) {
133            sRegistry = ITelephonyRegistry.Stub.asInterface(ServiceManager.getService(
134                    "telephony.registry"));
135        }
136    }
137
138    /** @hide */
139    private TelephonyManager() {
140        mContext = null;
141    }
142
143    private static TelephonyManager sInstance = new TelephonyManager();
144
145    /** @hide
146    /* @deprecated - use getSystemService as described above */
147    public static TelephonyManager getDefault() {
148        return sInstance;
149    }
150
151    private String getOpPackageName() {
152        // For legacy reasons the TelephonyManager has API for getting
153        // a static instance with no context set preventing us from
154        // getting the op package name. As a workaround we do a best
155        // effort and get the context from the current activity thread.
156        if (mContext != null) {
157            return mContext.getOpPackageName();
158        }
159        return ActivityThread.currentOpPackageName();
160    }
161
162    /**
163     * Returns the multi SIM variant
164     * Returns DSDS for Dual SIM Dual Standby
165     * Returns DSDA for Dual SIM Dual Active
166     * Returns TSTS for Triple SIM Triple Standby
167     * Returns UNKNOWN for others
168     */
169    /** {@hide} */
170    public MultiSimVariants getMultiSimConfiguration() {
171        String mSimConfig =
172            SystemProperties.get(TelephonyProperties.PROPERTY_MULTI_SIM_CONFIG);
173        if (mSimConfig.equals("dsds")) {
174            return MultiSimVariants.DSDS;
175        } else if (mSimConfig.equals("dsda")) {
176            return MultiSimVariants.DSDA;
177        } else if (mSimConfig.equals("tsts")) {
178            return MultiSimVariants.TSTS;
179        } else {
180            return MultiSimVariants.UNKNOWN;
181        }
182    }
183
184
185    /**
186     * Returns the number of phones available.
187     * Returns 0 if none of voice, sms, data is not supported
188     * Returns 1 for Single standby mode (Single SIM functionality)
189     * Returns 2 for Dual standby mode.(Dual SIM functionality)
190     */
191    public int getPhoneCount() {
192        int phoneCount = 1;
193        switch (getMultiSimConfiguration()) {
194            case UNKNOWN:
195                // if voice or sms or data is supported, return 1 otherwise 0
196                if (isVoiceCapable() || isSmsCapable()) {
197                    phoneCount = 1;
198                } else {
199                    // todo: try to clean this up further by getting rid of the nested conditions
200                    if (mContext == null) {
201                        phoneCount = 1;
202                    } else {
203                        // check for data support
204                        ConnectivityManager cm = (ConnectivityManager)mContext.getSystemService(
205                                Context.CONNECTIVITY_SERVICE);
206                        if (cm == null) {
207                            phoneCount = 1;
208                        } else {
209                            if (cm.isNetworkSupported(ConnectivityManager.TYPE_MOBILE)) {
210                                phoneCount = 1;
211                            } else {
212                                phoneCount = 0;
213                            }
214                        }
215                    }
216                }
217                break;
218            case DSDS:
219            case DSDA:
220                phoneCount = PhoneConstants.MAX_PHONE_COUNT_DUAL_SIM;
221                break;
222            case TSTS:
223                phoneCount = PhoneConstants.MAX_PHONE_COUNT_TRI_SIM;
224                break;
225        }
226        return phoneCount;
227    }
228
229    /** {@hide} */
230    public static TelephonyManager from(Context context) {
231        return (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
232    }
233
234    /** {@hide} */
235    public boolean isMultiSimEnabled() {
236        return (multiSimConfig.equals("dsds") || multiSimConfig.equals("dsda") ||
237            multiSimConfig.equals("tsts"));
238    }
239
240    //
241    // Broadcast Intent actions
242    //
243
244    /**
245     * Broadcast intent action indicating that the call state
246     * on the device has changed.
247     *
248     * <p>
249     * The {@link #EXTRA_STATE} extra indicates the new call state.
250     * If the new state is RINGING, a second extra
251     * {@link #EXTRA_INCOMING_NUMBER} provides the incoming phone number as
252     * a String.
253     *
254     * <p class="note">
255     * Requires the READ_PHONE_STATE permission.
256     *
257     * <p class="note">
258     * This was a {@link android.content.Context#sendStickyBroadcast sticky}
259     * broadcast in version 1.0, but it is no longer sticky.
260     * Instead, use {@link #getCallState} to synchronously query the current call state.
261     *
262     * @see #EXTRA_STATE
263     * @see #EXTRA_INCOMING_NUMBER
264     * @see #getCallState
265     */
266    @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
267    public static final String ACTION_PHONE_STATE_CHANGED =
268            "android.intent.action.PHONE_STATE";
269
270    /**
271     * The Phone app sends this intent when a user opts to respond-via-message during an incoming
272     * call. By default, the device's default SMS app consumes this message and sends a text message
273     * to the caller. A third party app can also provide this functionality by consuming this Intent
274     * with a {@link android.app.Service} and sending the message using its own messaging system.
275     * <p>The intent contains a URI (available from {@link android.content.Intent#getData})
276     * describing the recipient, using either the {@code sms:}, {@code smsto:}, {@code mms:},
277     * or {@code mmsto:} URI schema. Each of these URI schema carry the recipient information the
278     * same way: the path part of the URI contains the recipient's phone number or a comma-separated
279     * set of phone numbers if there are multiple recipients. For example, {@code
280     * smsto:2065551234}.</p>
281     *
282     * <p>The intent may also contain extras for the message text (in {@link
283     * android.content.Intent#EXTRA_TEXT}) and a message subject
284     * (in {@link android.content.Intent#EXTRA_SUBJECT}).</p>
285     *
286     * <p class="note"><strong>Note:</strong>
287     * The intent-filter that consumes this Intent needs to be in a {@link android.app.Service}
288     * that requires the
289     * permission {@link android.Manifest.permission#SEND_RESPOND_VIA_MESSAGE}.</p>
290     * <p>For example, the service that receives this intent can be declared in the manifest file
291     * with an intent filter like this:</p>
292     * <pre>
293     * &lt;!-- Service that delivers SMS messages received from the phone "quick response" -->
294     * &lt;service android:name=".HeadlessSmsSendService"
295     *          android:permission="android.permission.SEND_RESPOND_VIA_MESSAGE"
296     *          android:exported="true" >
297     *   &lt;intent-filter>
298     *     &lt;action android:name="android.intent.action.RESPOND_VIA_MESSAGE" />
299     *     &lt;category android:name="android.intent.category.DEFAULT" />
300     *     &lt;data android:scheme="sms" />
301     *     &lt;data android:scheme="smsto" />
302     *     &lt;data android:scheme="mms" />
303     *     &lt;data android:scheme="mmsto" />
304     *   &lt;/intent-filter>
305     * &lt;/service></pre>
306     * <p>
307     * Output: nothing.
308     */
309    @SdkConstant(SdkConstantType.SERVICE_ACTION)
310    public static final String ACTION_RESPOND_VIA_MESSAGE =
311            "android.intent.action.RESPOND_VIA_MESSAGE";
312
313    /**
314     * The emergency dialer may choose to present activities with intent filters for this
315     * action as emergency assistance buttons that launch the activity when clicked.
316     *
317     * @hide
318     */
319    @SdkConstant(SdkConstantType.ACTIVITY_INTENT_ACTION)
320    public static final String ACTION_EMERGENCY_ASSISTANCE =
321            "android.telephony.action.EMERGENCY_ASSISTANCE";
322
323    /**
324     * Open the voicemail settings activity to make changes to voicemail configuration.
325     */
326    @SdkConstant(SdkConstantType.ACTIVITY_INTENT_ACTION)
327    public static final String ACTION_CONFIGURE_VOICEMAIL =
328            "android.telephony.action.CONFIGURE_VOICEMAIL";
329
330    /**
331     * @hide
332     */
333    public static final boolean EMERGENCY_ASSISTANCE_ENABLED = true;
334
335    /**
336     * The lookup key used with the {@link #ACTION_PHONE_STATE_CHANGED} broadcast
337     * for a String containing the new call state.
338     *
339     * @see #EXTRA_STATE_IDLE
340     * @see #EXTRA_STATE_RINGING
341     * @see #EXTRA_STATE_OFFHOOK
342     *
343     * <p class="note">
344     * Retrieve with
345     * {@link android.content.Intent#getStringExtra(String)}.
346     */
347    public static final String EXTRA_STATE = PhoneConstants.STATE_KEY;
348
349    /**
350     * Value used with {@link #EXTRA_STATE} corresponding to
351     * {@link #CALL_STATE_IDLE}.
352     */
353    public static final String EXTRA_STATE_IDLE = PhoneConstants.State.IDLE.toString();
354
355    /**
356     * Value used with {@link #EXTRA_STATE} corresponding to
357     * {@link #CALL_STATE_RINGING}.
358     */
359    public static final String EXTRA_STATE_RINGING = PhoneConstants.State.RINGING.toString();
360
361    /**
362     * Value used with {@link #EXTRA_STATE} corresponding to
363     * {@link #CALL_STATE_OFFHOOK}.
364     */
365    public static final String EXTRA_STATE_OFFHOOK = PhoneConstants.State.OFFHOOK.toString();
366
367    /**
368     * The lookup key used with the {@link #ACTION_PHONE_STATE_CHANGED} broadcast
369     * for a String containing the incoming phone number.
370     * Only valid when the new call state is RINGING.
371     *
372     * <p class="note">
373     * Retrieve with
374     * {@link android.content.Intent#getStringExtra(String)}.
375     */
376    public static final String EXTRA_INCOMING_NUMBER = "incoming_number";
377
378    /**
379     * Broadcast intent action indicating that a precise call state
380     * (cellular) on the device has changed.
381     *
382     * <p>
383     * The {@link #EXTRA_RINGING_CALL_STATE} extra indicates the ringing call state.
384     * The {@link #EXTRA_FOREGROUND_CALL_STATE} extra indicates the foreground call state.
385     * The {@link #EXTRA_BACKGROUND_CALL_STATE} extra indicates the background call state.
386     * The {@link #EXTRA_DISCONNECT_CAUSE} extra indicates the disconnect cause.
387     * The {@link #EXTRA_PRECISE_DISCONNECT_CAUSE} extra indicates the precise disconnect cause.
388     *
389     * <p class="note">
390     * Requires the READ_PRECISE_PHONE_STATE permission.
391     *
392     * @see #EXTRA_RINGING_CALL_STATE
393     * @see #EXTRA_FOREGROUND_CALL_STATE
394     * @see #EXTRA_BACKGROUND_CALL_STATE
395     * @see #EXTRA_DISCONNECT_CAUSE
396     * @see #EXTRA_PRECISE_DISCONNECT_CAUSE
397     *
398     * <p class="note">
399     * Requires the READ_PRECISE_PHONE_STATE permission.
400     *
401     * @hide
402     */
403    @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
404    public static final String ACTION_PRECISE_CALL_STATE_CHANGED =
405            "android.intent.action.PRECISE_CALL_STATE";
406
407    /**
408     * The lookup key used with the {@link #ACTION_PRECISE_CALL_STATE_CHANGED} broadcast
409     * for an integer containing the state of the current ringing call.
410     *
411     * @see PreciseCallState#PRECISE_CALL_STATE_NOT_VALID
412     * @see PreciseCallState#PRECISE_CALL_STATE_IDLE
413     * @see PreciseCallState#PRECISE_CALL_STATE_ACTIVE
414     * @see PreciseCallState#PRECISE_CALL_STATE_HOLDING
415     * @see PreciseCallState#PRECISE_CALL_STATE_DIALING
416     * @see PreciseCallState#PRECISE_CALL_STATE_ALERTING
417     * @see PreciseCallState#PRECISE_CALL_STATE_INCOMING
418     * @see PreciseCallState#PRECISE_CALL_STATE_WAITING
419     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTED
420     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTING
421     *
422     * <p class="note">
423     * Retrieve with
424     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
425     *
426     * @hide
427     */
428    public static final String EXTRA_RINGING_CALL_STATE = "ringing_state";
429
430    /**
431     * The lookup key used with the {@link #ACTION_PRECISE_CALL_STATE_CHANGED} broadcast
432     * for an integer containing the state of the current foreground call.
433     *
434     * @see PreciseCallState#PRECISE_CALL_STATE_NOT_VALID
435     * @see PreciseCallState#PRECISE_CALL_STATE_IDLE
436     * @see PreciseCallState#PRECISE_CALL_STATE_ACTIVE
437     * @see PreciseCallState#PRECISE_CALL_STATE_HOLDING
438     * @see PreciseCallState#PRECISE_CALL_STATE_DIALING
439     * @see PreciseCallState#PRECISE_CALL_STATE_ALERTING
440     * @see PreciseCallState#PRECISE_CALL_STATE_INCOMING
441     * @see PreciseCallState#PRECISE_CALL_STATE_WAITING
442     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTED
443     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTING
444     *
445     * <p class="note">
446     * Retrieve with
447     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
448     *
449     * @hide
450     */
451    public static final String EXTRA_FOREGROUND_CALL_STATE = "foreground_state";
452
453    /**
454     * The lookup key used with the {@link #ACTION_PRECISE_CALL_STATE_CHANGED} broadcast
455     * for an integer containing the state of the current background call.
456     *
457     * @see PreciseCallState#PRECISE_CALL_STATE_NOT_VALID
458     * @see PreciseCallState#PRECISE_CALL_STATE_IDLE
459     * @see PreciseCallState#PRECISE_CALL_STATE_ACTIVE
460     * @see PreciseCallState#PRECISE_CALL_STATE_HOLDING
461     * @see PreciseCallState#PRECISE_CALL_STATE_DIALING
462     * @see PreciseCallState#PRECISE_CALL_STATE_ALERTING
463     * @see PreciseCallState#PRECISE_CALL_STATE_INCOMING
464     * @see PreciseCallState#PRECISE_CALL_STATE_WAITING
465     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTED
466     * @see PreciseCallState#PRECISE_CALL_STATE_DISCONNECTING
467     *
468     * <p class="note">
469     * Retrieve with
470     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
471     *
472     * @hide
473     */
474    public static final String EXTRA_BACKGROUND_CALL_STATE = "background_state";
475
476    /**
477     * The lookup key used with the {@link #ACTION_PRECISE_CALL_STATE_CHANGED} broadcast
478     * for an integer containing the disconnect cause.
479     *
480     * @see DisconnectCause
481     *
482     * <p class="note">
483     * Retrieve with
484     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
485     *
486     * @hide
487     */
488    public static final String EXTRA_DISCONNECT_CAUSE = "disconnect_cause";
489
490    /**
491     * The lookup key used with the {@link #ACTION_PRECISE_CALL_STATE_CHANGED} broadcast
492     * for an integer containing the disconnect cause provided by the RIL.
493     *
494     * @see PreciseDisconnectCause
495     *
496     * <p class="note">
497     * Retrieve with
498     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
499     *
500     * @hide
501     */
502    public static final String EXTRA_PRECISE_DISCONNECT_CAUSE = "precise_disconnect_cause";
503
504    /**
505     * Broadcast intent action indicating a data connection has changed,
506     * providing precise information about the connection.
507     *
508     * <p>
509     * The {@link #EXTRA_DATA_STATE} extra indicates the connection state.
510     * The {@link #EXTRA_DATA_NETWORK_TYPE} extra indicates the connection network type.
511     * The {@link #EXTRA_DATA_APN_TYPE} extra indicates the APN type.
512     * The {@link #EXTRA_DATA_APN} extra indicates the APN.
513     * The {@link #EXTRA_DATA_CHANGE_REASON} extra indicates the connection change reason.
514     * The {@link #EXTRA_DATA_IFACE_PROPERTIES} extra indicates the connection interface.
515     * The {@link #EXTRA_DATA_FAILURE_CAUSE} extra indicates the connection fail cause.
516     *
517     * <p class="note">
518     * Requires the READ_PRECISE_PHONE_STATE permission.
519     *
520     * @see #EXTRA_DATA_STATE
521     * @see #EXTRA_DATA_NETWORK_TYPE
522     * @see #EXTRA_DATA_APN_TYPE
523     * @see #EXTRA_DATA_APN
524     * @see #EXTRA_DATA_CHANGE_REASON
525     * @see #EXTRA_DATA_IFACE
526     * @see #EXTRA_DATA_FAILURE_CAUSE
527     * @hide
528     */
529    @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
530    public static final String ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED =
531            "android.intent.action.PRECISE_DATA_CONNECTION_STATE_CHANGED";
532
533    /**
534     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
535     * for an integer containing the state of the current data connection.
536     *
537     * @see TelephonyManager#DATA_UNKNOWN
538     * @see TelephonyManager#DATA_DISCONNECTED
539     * @see TelephonyManager#DATA_CONNECTING
540     * @see TelephonyManager#DATA_CONNECTED
541     * @see TelephonyManager#DATA_SUSPENDED
542     *
543     * <p class="note">
544     * Retrieve with
545     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
546     *
547     * @hide
548     */
549    public static final String EXTRA_DATA_STATE = PhoneConstants.STATE_KEY;
550
551    /**
552     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
553     * for an integer containing the network type.
554     *
555     * @see TelephonyManager#NETWORK_TYPE_UNKNOWN
556     * @see TelephonyManager#NETWORK_TYPE_GPRS
557     * @see TelephonyManager#NETWORK_TYPE_EDGE
558     * @see TelephonyManager#NETWORK_TYPE_UMTS
559     * @see TelephonyManager#NETWORK_TYPE_CDMA
560     * @see TelephonyManager#NETWORK_TYPE_EVDO_0
561     * @see TelephonyManager#NETWORK_TYPE_EVDO_A
562     * @see TelephonyManager#NETWORK_TYPE_1xRTT
563     * @see TelephonyManager#NETWORK_TYPE_HSDPA
564     * @see TelephonyManager#NETWORK_TYPE_HSUPA
565     * @see TelephonyManager#NETWORK_TYPE_HSPA
566     * @see TelephonyManager#NETWORK_TYPE_IDEN
567     * @see TelephonyManager#NETWORK_TYPE_EVDO_B
568     * @see TelephonyManager#NETWORK_TYPE_LTE
569     * @see TelephonyManager#NETWORK_TYPE_EHRPD
570     * @see TelephonyManager#NETWORK_TYPE_HSPAP
571     *
572     * <p class="note">
573     * Retrieve with
574     * {@link android.content.Intent#getIntExtra(String name, int defaultValue)}.
575     *
576     * @hide
577     */
578    public static final String EXTRA_DATA_NETWORK_TYPE = PhoneConstants.DATA_NETWORK_TYPE_KEY;
579
580    /**
581     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
582     * for an String containing the data APN type.
583     *
584     * <p class="note">
585     * Retrieve with
586     * {@link android.content.Intent#getStringExtra(String name)}.
587     *
588     * @hide
589     */
590    public static final String EXTRA_DATA_APN_TYPE = PhoneConstants.DATA_APN_TYPE_KEY;
591
592    /**
593     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
594     * for an String containing the data APN.
595     *
596     * <p class="note">
597     * Retrieve with
598     * {@link android.content.Intent#getStringExtra(String name)}.
599     *
600     * @hide
601     */
602    public static final String EXTRA_DATA_APN = PhoneConstants.DATA_APN_KEY;
603
604    /**
605     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
606     * for an String representation of the change reason.
607     *
608     * <p class="note">
609     * Retrieve with
610     * {@link android.content.Intent#getStringExtra(String name)}.
611     *
612     * @hide
613     */
614    public static final String EXTRA_DATA_CHANGE_REASON = PhoneConstants.STATE_CHANGE_REASON_KEY;
615
616    /**
617     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
618     * for an String representation of the data interface.
619     *
620     * <p class="note">
621     * Retrieve with
622     * {@link android.content.Intent#getParcelableExtra(String name)}.
623     *
624     * @hide
625     */
626    public static final String EXTRA_DATA_LINK_PROPERTIES_KEY = PhoneConstants.DATA_LINK_PROPERTIES_KEY;
627
628    /**
629     * The lookup key used with the {@link #ACTION_PRECISE_DATA_CONNECTION_STATE_CHANGED} broadcast
630     * for the data connection fail cause.
631     *
632     * <p class="note">
633     * Retrieve with
634     * {@link android.content.Intent#getStringExtra(String name)}.
635     *
636     * @hide
637     */
638    public static final String EXTRA_DATA_FAILURE_CAUSE = PhoneConstants.DATA_FAILURE_CAUSE_KEY;
639
640    /**
641     * Broadcast intent action for letting custom component know to show voicemail notification.
642     * @hide
643     */
644    @SystemApi
645    public static final String ACTION_SHOW_VOICEMAIL_NOTIFICATION =
646            "android.telephony.action.SHOW_VOICEMAIL_NOTIFICATION";
647
648    /**
649     * The number of voice messages associated with the notification.
650     * @hide
651     */
652    @SystemApi
653    public static final String EXTRA_NOTIFICATION_COUNT =
654            "android.telephony.extra.NOTIFICATION_COUNT";
655
656    /**
657     * The voicemail number.
658     * @hide
659     */
660    @SystemApi
661    public static final String EXTRA_VOICEMAIL_NUMBER =
662            "android.telephony.extra.VOICEMAIL_NUMBER";
663
664    /**
665     * The intent to call voicemail.
666     * @hide
667     */
668    @SystemApi
669    public static final String EXTRA_CALL_VOICEMAIL_INTENT =
670            "android.telephony.extra.CALL_VOICEMAIL_INTENT";
671
672    /**
673     * The intent to launch voicemail settings.
674     * @hide
675     */
676    @SystemApi
677    public static final String EXTRA_LAUNCH_VOICEMAIL_SETTINGS_INTENT =
678            "android.telephony.extra.LAUNCH_VOICEMAIL_SETTINGS_INTENT";
679
680    /**
681     * Response codes for sim activation. Activation completed successfully.
682     * @hide
683     */
684    @SystemApi
685    public static final int SIM_ACTIVATION_RESULT_COMPLETE = 0;
686    /**
687     * Response codes for sim activation. Activation not supported (device has no SIM).
688     * @hide
689     */
690    @SystemApi
691    public static final int SIM_ACTIVATION_RESULT_NOT_SUPPORTED = 1;
692    /**
693     * Response codes for sim activation. Activation is in progress.
694     * @hide
695     */
696    @SystemApi
697    public static final int SIM_ACTIVATION_RESULT_IN_PROGRESS = 2;
698    /**
699     * Response codes for sim activation. Activation failed to complete.
700     * @hide
701     */
702    @SystemApi
703    public static final int SIM_ACTIVATION_RESULT_FAILED = 3;
704    /**
705     * Response codes for sim activation. Activation canceled by user.
706     * @hide
707     */
708    @SystemApi
709    public static final int SIM_ACTIVATION_RESULT_CANCELED = 4;
710
711    /* Visual voicemail protocols */
712
713    /**
714     * The OMTP protocol.
715     */
716    public static final String VVM_TYPE_OMTP = "vvm_type_omtp";
717
718    /**
719     * A flavor of OMTP protocol with a different mobile originated (MO) format
720     */
721    public static final String VVM_TYPE_CVVM = "vvm_type_cvvm";
722
723    /* Visual voicemail SMS filter constants */
724
725    /**
726     * The visual voicemail SMS message does not have to be a data SMS, and can be directed to any
727     * port.
728     * @hide
729     */
730    public static final int VVM_SMS_FILTER_DESTINATION_PORT_ANY = -1;
731
732    /**
733     * The visual voicemail SMS message can be directed to any port, but must be a data SMS.
734     * @hide
735     */
736    public static final int VVM_SMS_FILTER_DESTINATION_PORT_DATA_SMS = -2;
737
738    //
739    //
740    // Device Info
741    //
742    //
743
744    /**
745     * Returns the software version number for the device, for example,
746     * the IMEI/SV for GSM phones. Return null if the software version is
747     * not available.
748     *
749     * <p>Requires Permission:
750     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
751     */
752    public String getDeviceSoftwareVersion() {
753        return getDeviceSoftwareVersion(getDefaultSim());
754    }
755
756    /**
757     * Returns the software version number for the device, for example,
758     * the IMEI/SV for GSM phones. Return null if the software version is
759     * not available.
760     *
761     * <p>Requires Permission:
762     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
763     *
764     * @param slotId of which deviceID is returned
765     */
766    /** {@hide} */
767    public String getDeviceSoftwareVersion(int slotId) {
768        ITelephony telephony = getITelephony();
769        if (telephony == null) return null;
770
771        try {
772            return telephony.getDeviceSoftwareVersionForSlot(slotId, getOpPackageName());
773        } catch (RemoteException ex) {
774            return null;
775        } catch (NullPointerException ex) {
776            return null;
777        }
778    }
779
780    /**
781     * Returns the unique device ID, for example, the IMEI for GSM and the MEID
782     * or ESN for CDMA phones. Return null if device ID is not available.
783     *
784     * <p>Requires Permission:
785     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
786     */
787    public String getDeviceId() {
788        try {
789            ITelephony telephony = getITelephony();
790            if (telephony == null)
791                return null;
792            return telephony.getDeviceId(mContext.getOpPackageName());
793        } catch (RemoteException ex) {
794            return null;
795        } catch (NullPointerException ex) {
796            return null;
797        }
798    }
799
800    /**
801     * Returns the unique device ID of a subscription, for example, the IMEI for
802     * GSM and the MEID for CDMA phones. Return null if device ID is not available.
803     *
804     * <p>Requires Permission:
805     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
806     *
807     * @param slotId of which deviceID is returned
808     */
809    public String getDeviceId(int slotId) {
810        // FIXME this assumes phoneId == slotId
811        try {
812            IPhoneSubInfo info = getSubscriberInfo();
813            if (info == null)
814                return null;
815            return info.getDeviceIdForPhone(slotId, mContext.getOpPackageName());
816        } catch (RemoteException ex) {
817            return null;
818        } catch (NullPointerException ex) {
819            return null;
820        }
821    }
822
823    /**
824     * Returns the IMEI. Return null if IMEI is not available.
825     *
826     * <p>Requires Permission:
827     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
828     */
829    /** {@hide} */
830    public String getImei() {
831        return getImei(getDefaultSim());
832    }
833
834    /**
835     * Returns the IMEI. Return null if IMEI is not available.
836     *
837     * <p>Requires Permission:
838     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
839     *
840     * @param slotId of which deviceID is returned
841     */
842    /** {@hide} */
843    public String getImei(int slotId) {
844        ITelephony telephony = getITelephony();
845        if (telephony == null) return null;
846
847        try {
848            return telephony.getImeiForSlot(slotId, getOpPackageName());
849        } catch (RemoteException ex) {
850            return null;
851        } catch (NullPointerException ex) {
852            return null;
853        }
854    }
855
856    /**
857     * Returns the NAI. Return null if NAI is not available.
858     *
859     */
860    /** {@hide}*/
861    public String getNai() {
862        return getNai(getDefaultSim());
863    }
864
865    /**
866     * Returns the NAI. Return null if NAI is not available.
867     *
868     *  @param slotId of which Nai is returned
869     */
870    /** {@hide}*/
871    public String getNai(int slotId) {
872        int[] subId = SubscriptionManager.getSubId(slotId);
873        try {
874            IPhoneSubInfo info = getSubscriberInfo();
875            if (info == null)
876                return null;
877            String nai = info.getNaiForSubscriber(subId[0], mContext.getOpPackageName());
878            if (Log.isLoggable(TAG, Log.VERBOSE)) {
879                Rlog.v(TAG, "Nai = " + nai);
880            }
881            return nai;
882        } catch (RemoteException ex) {
883            return null;
884        } catch (NullPointerException ex) {
885            return null;
886        }
887    }
888
889    /**
890     * Returns the current location of the device.
891     *<p>
892     * If there is only one radio in the device and that radio has an LTE connection,
893     * this method will return null. The implementation must not to try add LTE
894     * identifiers into the existing cdma/gsm classes.
895     *<p>
896     * In the future this call will be deprecated.
897     *<p>
898     * @return Current location of the device or null if not available.
899     *
900     * <p>Requires Permission:
901     * {@link android.Manifest.permission#ACCESS_COARSE_LOCATION ACCESS_COARSE_LOCATION} or
902     * {@link android.Manifest.permission#ACCESS_COARSE_LOCATION ACCESS_FINE_LOCATION}.
903     */
904    public CellLocation getCellLocation() {
905        try {
906            ITelephony telephony = getITelephony();
907            if (telephony == null) {
908                Rlog.d(TAG, "getCellLocation returning null because telephony is null");
909                return null;
910            }
911            Bundle bundle = telephony.getCellLocation(mContext.getOpPackageName());
912            if (bundle.isEmpty()) {
913                Rlog.d(TAG, "getCellLocation returning null because bundle is empty");
914                return null;
915            }
916            CellLocation cl = CellLocation.newFromBundle(bundle);
917            if (cl.isEmpty()) {
918                Rlog.d(TAG, "getCellLocation returning null because CellLocation is empty");
919                return null;
920            }
921            return cl;
922        } catch (RemoteException ex) {
923            Rlog.d(TAG, "getCellLocation returning null due to RemoteException " + ex);
924            return null;
925        } catch (NullPointerException ex) {
926            Rlog.d(TAG, "getCellLocation returning null due to NullPointerException " + ex);
927            return null;
928        }
929    }
930
931    /**
932     * Enables location update notifications.  {@link PhoneStateListener#onCellLocationChanged
933     * PhoneStateListener.onCellLocationChanged} will be called on location updates.
934     *
935     * <p>Requires Permission: {@link android.Manifest.permission#CONTROL_LOCATION_UPDATES
936     * CONTROL_LOCATION_UPDATES}
937     *
938     * @hide
939     */
940    public void enableLocationUpdates() {
941            enableLocationUpdates(getDefaultSubscription());
942    }
943
944    /**
945     * Enables location update notifications for a subscription.
946     * {@link PhoneStateListener#onCellLocationChanged
947     * PhoneStateListener.onCellLocationChanged} will be called on location updates.
948     *
949     * <p>Requires Permission: {@link android.Manifest.permission#CONTROL_LOCATION_UPDATES
950     * CONTROL_LOCATION_UPDATES}
951     *
952     * @param subId for which the location updates are enabled
953     */
954    /** @hide */
955    public void enableLocationUpdates(int subId) {
956        try {
957            ITelephony telephony = getITelephony();
958            if (telephony != null)
959                telephony.enableLocationUpdatesForSubscriber(subId);
960        } catch (RemoteException ex) {
961        } catch (NullPointerException ex) {
962        }
963    }
964
965    /**
966     * Disables location update notifications.  {@link PhoneStateListener#onCellLocationChanged
967     * PhoneStateListener.onCellLocationChanged} will be called on location updates.
968     *
969     * <p>Requires Permission: {@link android.Manifest.permission#CONTROL_LOCATION_UPDATES
970     * CONTROL_LOCATION_UPDATES}
971     *
972     * @hide
973     */
974    public void disableLocationUpdates() {
975            disableLocationUpdates(getDefaultSubscription());
976    }
977
978    /** @hide */
979    public void disableLocationUpdates(int subId) {
980        try {
981            ITelephony telephony = getITelephony();
982            if (telephony != null)
983                telephony.disableLocationUpdatesForSubscriber(subId);
984        } catch (RemoteException ex) {
985        } catch (NullPointerException ex) {
986        }
987    }
988
989    /**
990     * Returns the neighboring cell information of the device.
991     *
992     * @return List of NeighboringCellInfo or null if info unavailable.
993     *
994     * <p>Requires Permission:
995     * (@link android.Manifest.permission#ACCESS_COARSE_UPDATES}
996     *
997     * @deprecated Use (@link getAllCellInfo} which returns a superset of the information
998     *             from NeighboringCellInfo.
999     */
1000    @Deprecated
1001    public List<NeighboringCellInfo> getNeighboringCellInfo() {
1002        try {
1003            ITelephony telephony = getITelephony();
1004            if (telephony == null)
1005                return null;
1006            return telephony.getNeighboringCellInfo(mContext.getOpPackageName());
1007        } catch (RemoteException ex) {
1008            return null;
1009        } catch (NullPointerException ex) {
1010            return null;
1011        }
1012    }
1013
1014    /** No phone radio. */
1015    public static final int PHONE_TYPE_NONE = PhoneConstants.PHONE_TYPE_NONE;
1016    /** Phone radio is GSM. */
1017    public static final int PHONE_TYPE_GSM = PhoneConstants.PHONE_TYPE_GSM;
1018    /** Phone radio is CDMA. */
1019    public static final int PHONE_TYPE_CDMA = PhoneConstants.PHONE_TYPE_CDMA;
1020    /** Phone is via SIP. */
1021    public static final int PHONE_TYPE_SIP = PhoneConstants.PHONE_TYPE_SIP;
1022
1023    /**
1024     * Returns the current phone type.
1025     * TODO: This is a last minute change and hence hidden.
1026     *
1027     * @see #PHONE_TYPE_NONE
1028     * @see #PHONE_TYPE_GSM
1029     * @see #PHONE_TYPE_CDMA
1030     * @see #PHONE_TYPE_SIP
1031     *
1032     * {@hide}
1033     */
1034    @SystemApi
1035    public int getCurrentPhoneType() {
1036        return getCurrentPhoneType(getDefaultSubscription());
1037    }
1038
1039    /**
1040     * Returns a constant indicating the device phone type for a subscription.
1041     *
1042     * @see #PHONE_TYPE_NONE
1043     * @see #PHONE_TYPE_GSM
1044     * @see #PHONE_TYPE_CDMA
1045     *
1046     * @param subId for which phone type is returned
1047     */
1048    /** {@hide} */
1049    @SystemApi
1050    public int getCurrentPhoneType(int subId) {
1051        int phoneId;
1052        if (subId == SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
1053            // if we don't have any sims, we don't have subscriptions, but we
1054            // still may want to know what type of phone we've got.
1055            phoneId = 0;
1056        } else {
1057            phoneId = SubscriptionManager.getPhoneId(subId);
1058        }
1059
1060        return getCurrentPhoneTypeForSlot(phoneId);
1061    }
1062
1063    /**
1064     * See getCurrentPhoneType.
1065     *
1066     * @hide
1067     */
1068    public int getCurrentPhoneTypeForSlot(int slotId) {
1069        try{
1070            ITelephony telephony = getITelephony();
1071            if (telephony != null) {
1072                return telephony.getActivePhoneTypeForSlot(slotId);
1073            } else {
1074                // This can happen when the ITelephony interface is not up yet.
1075                return getPhoneTypeFromProperty(slotId);
1076            }
1077        } catch (RemoteException ex) {
1078            // This shouldn't happen in the normal case, as a backup we
1079            // read from the system property.
1080            return getPhoneTypeFromProperty(slotId);
1081        } catch (NullPointerException ex) {
1082            // This shouldn't happen in the normal case, as a backup we
1083            // read from the system property.
1084            return getPhoneTypeFromProperty(slotId);
1085        }
1086    }
1087
1088    /**
1089     * Returns a constant indicating the device phone type.  This
1090     * indicates the type of radio used to transmit voice calls.
1091     *
1092     * @see #PHONE_TYPE_NONE
1093     * @see #PHONE_TYPE_GSM
1094     * @see #PHONE_TYPE_CDMA
1095     * @see #PHONE_TYPE_SIP
1096     */
1097    public int getPhoneType() {
1098        if (!isVoiceCapable()) {
1099            return PHONE_TYPE_NONE;
1100        }
1101        return getCurrentPhoneType();
1102    }
1103
1104    private int getPhoneTypeFromProperty() {
1105        return getPhoneTypeFromProperty(getDefaultPhone());
1106    }
1107
1108    /** {@hide} */
1109    private int getPhoneTypeFromProperty(int phoneId) {
1110        String type = getTelephonyProperty(phoneId,
1111                TelephonyProperties.CURRENT_ACTIVE_PHONE, null);
1112        if (type == null || type.equals("")) {
1113            return getPhoneTypeFromNetworkType(phoneId);
1114        }
1115        return Integer.parseInt(type);
1116    }
1117
1118    private int getPhoneTypeFromNetworkType() {
1119        return getPhoneTypeFromNetworkType(getDefaultPhone());
1120    }
1121
1122    /** {@hide} */
1123    private int getPhoneTypeFromNetworkType(int phoneId) {
1124        // When the system property CURRENT_ACTIVE_PHONE, has not been set,
1125        // use the system property for default network type.
1126        // This is a fail safe, and can only happen at first boot.
1127        String mode = getTelephonyProperty(phoneId, "ro.telephony.default_network", null);
1128        if (mode != null) {
1129            return TelephonyManager.getPhoneType(Integer.parseInt(mode));
1130        }
1131        return TelephonyManager.PHONE_TYPE_NONE;
1132    }
1133
1134    /**
1135     * This function returns the type of the phone, depending
1136     * on the network mode.
1137     *
1138     * @param networkMode
1139     * @return Phone Type
1140     *
1141     * @hide
1142     */
1143    public static int getPhoneType(int networkMode) {
1144        switch(networkMode) {
1145        case RILConstants.NETWORK_MODE_CDMA:
1146        case RILConstants.NETWORK_MODE_CDMA_NO_EVDO:
1147        case RILConstants.NETWORK_MODE_EVDO_NO_CDMA:
1148            return PhoneConstants.PHONE_TYPE_CDMA;
1149
1150        case RILConstants.NETWORK_MODE_WCDMA_PREF:
1151        case RILConstants.NETWORK_MODE_GSM_ONLY:
1152        case RILConstants.NETWORK_MODE_WCDMA_ONLY:
1153        case RILConstants.NETWORK_MODE_GSM_UMTS:
1154        case RILConstants.NETWORK_MODE_LTE_GSM_WCDMA:
1155        case RILConstants.NETWORK_MODE_LTE_WCDMA:
1156        case RILConstants.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA:
1157        case RILConstants.NETWORK_MODE_TDSCDMA_ONLY:
1158        case RILConstants.NETWORK_MODE_TDSCDMA_WCDMA:
1159        case RILConstants.NETWORK_MODE_LTE_TDSCDMA:
1160        case RILConstants.NETWORK_MODE_TDSCDMA_GSM:
1161        case RILConstants.NETWORK_MODE_LTE_TDSCDMA_GSM:
1162        case RILConstants.NETWORK_MODE_TDSCDMA_GSM_WCDMA:
1163        case RILConstants.NETWORK_MODE_LTE_TDSCDMA_WCDMA:
1164        case RILConstants.NETWORK_MODE_LTE_TDSCDMA_GSM_WCDMA:
1165        case RILConstants.NETWORK_MODE_LTE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1166            return PhoneConstants.PHONE_TYPE_GSM;
1167
1168        // Use CDMA Phone for the global mode including CDMA
1169        case RILConstants.NETWORK_MODE_GLOBAL:
1170        case RILConstants.NETWORK_MODE_LTE_CDMA_EVDO:
1171        case RILConstants.NETWORK_MODE_TDSCDMA_CDMA_EVDO_GSM_WCDMA:
1172            return PhoneConstants.PHONE_TYPE_CDMA;
1173
1174        case RILConstants.NETWORK_MODE_LTE_ONLY:
1175            if (getLteOnCdmaModeStatic() == PhoneConstants.LTE_ON_CDMA_TRUE) {
1176                return PhoneConstants.PHONE_TYPE_CDMA;
1177            } else {
1178                return PhoneConstants.PHONE_TYPE_GSM;
1179            }
1180        default:
1181            return PhoneConstants.PHONE_TYPE_GSM;
1182        }
1183    }
1184
1185    /**
1186     * The contents of the /proc/cmdline file
1187     */
1188    private static String getProcCmdLine()
1189    {
1190        String cmdline = "";
1191        FileInputStream is = null;
1192        try {
1193            is = new FileInputStream("/proc/cmdline");
1194            byte [] buffer = new byte[2048];
1195            int count = is.read(buffer);
1196            if (count > 0) {
1197                cmdline = new String(buffer, 0, count);
1198            }
1199        } catch (IOException e) {
1200            Rlog.d(TAG, "No /proc/cmdline exception=" + e);
1201        } finally {
1202            if (is != null) {
1203                try {
1204                    is.close();
1205                } catch (IOException e) {
1206                }
1207            }
1208        }
1209        Rlog.d(TAG, "/proc/cmdline=" + cmdline);
1210        return cmdline;
1211    }
1212
1213    /** Kernel command line */
1214    private static final String sKernelCmdLine = getProcCmdLine();
1215
1216    /** Pattern for selecting the product type from the kernel command line */
1217    private static final Pattern sProductTypePattern =
1218        Pattern.compile("\\sproduct_type\\s*=\\s*(\\w+)");
1219
1220    /** The ProductType used for LTE on CDMA devices */
1221    private static final String sLteOnCdmaProductType =
1222        SystemProperties.get(TelephonyProperties.PROPERTY_LTE_ON_CDMA_PRODUCT_TYPE, "");
1223
1224    /**
1225     * Return if the current radio is LTE on CDMA. This
1226     * is a tri-state return value as for a period of time
1227     * the mode may be unknown.
1228     *
1229     * @return {@link PhoneConstants#LTE_ON_CDMA_UNKNOWN}, {@link PhoneConstants#LTE_ON_CDMA_FALSE}
1230     * or {@link PhoneConstants#LTE_ON_CDMA_TRUE}
1231     *
1232     * @hide
1233     */
1234    public static int getLteOnCdmaModeStatic() {
1235        int retVal;
1236        int curVal;
1237        String productType = "";
1238
1239        curVal = SystemProperties.getInt(TelephonyProperties.PROPERTY_LTE_ON_CDMA_DEVICE,
1240                    PhoneConstants.LTE_ON_CDMA_UNKNOWN);
1241        retVal = curVal;
1242        if (retVal == PhoneConstants.LTE_ON_CDMA_UNKNOWN) {
1243            Matcher matcher = sProductTypePattern.matcher(sKernelCmdLine);
1244            if (matcher.find()) {
1245                productType = matcher.group(1);
1246                if (sLteOnCdmaProductType.equals(productType)) {
1247                    retVal = PhoneConstants.LTE_ON_CDMA_TRUE;
1248                } else {
1249                    retVal = PhoneConstants.LTE_ON_CDMA_FALSE;
1250                }
1251            } else {
1252                retVal = PhoneConstants.LTE_ON_CDMA_FALSE;
1253            }
1254        }
1255
1256        Rlog.d(TAG, "getLteOnCdmaMode=" + retVal + " curVal=" + curVal +
1257                " product_type='" + productType +
1258                "' lteOnCdmaProductType='" + sLteOnCdmaProductType + "'");
1259        return retVal;
1260    }
1261
1262    //
1263    //
1264    // Current Network
1265    //
1266    //
1267
1268    /**
1269     * Returns the alphabetic name of current registered operator.
1270     * <p>
1271     * Availability: Only when user is registered to a network. Result may be
1272     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1273     * on a CDMA network).
1274     */
1275    public String getNetworkOperatorName() {
1276        return getNetworkOperatorName(getDefaultSubscription());
1277    }
1278
1279    /**
1280     * Returns the alphabetic name of current registered operator
1281     * for a particular subscription.
1282     * <p>
1283     * Availability: Only when user is registered to a network. Result may be
1284     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1285     * on a CDMA network).
1286     * @param subId
1287     */
1288    public String getNetworkOperatorName(int subId) {
1289        int phoneId = SubscriptionManager.getPhoneId(subId);
1290        return getTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_ALPHA, "");
1291    }
1292
1293    /**
1294     * Returns the numeric name (MCC+MNC) of current registered operator.
1295     * <p>
1296     * Availability: Only when user is registered to a network. Result may be
1297     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1298     * on a CDMA network).
1299     */
1300    public String getNetworkOperator() {
1301        return getNetworkOperatorForPhone(getDefaultPhone());
1302    }
1303
1304    /**
1305     * Returns the numeric name (MCC+MNC) of current registered operator
1306     * for a particular subscription.
1307     * <p>
1308     * Availability: Only when user is registered to a network. Result may be
1309     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1310     * on a CDMA network).
1311     *
1312     * @param subId
1313     */
1314    public String getNetworkOperator(int subId) {
1315        int phoneId = SubscriptionManager.getPhoneId(subId);
1316        return getNetworkOperatorForPhone(phoneId);
1317     }
1318
1319    /**
1320     * Returns the numeric name (MCC+MNC) of current registered operator
1321     * for a particular subscription.
1322     * <p>
1323     * Availability: Only when user is registered to a network. Result may be
1324     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1325     * on a CDMA network).
1326     *
1327     * @param phoneId
1328     * @hide
1329     **/
1330    public String getNetworkOperatorForPhone(int phoneId) {
1331        return getTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_NUMERIC, "");
1332     }
1333
1334    /**
1335     * Returns true if the device is considered roaming on the current
1336     * network, for GSM purposes.
1337     * <p>
1338     * Availability: Only when user registered to a network.
1339     */
1340    public boolean isNetworkRoaming() {
1341        return isNetworkRoaming(getDefaultSubscription());
1342    }
1343
1344    /**
1345     * Returns true if the device is considered roaming on the current
1346     * network for a subscription.
1347     * <p>
1348     * Availability: Only when user registered to a network.
1349     *
1350     * @param subId
1351     */
1352    public boolean isNetworkRoaming(int subId) {
1353        int phoneId = SubscriptionManager.getPhoneId(subId);
1354        return Boolean.parseBoolean(getTelephonyProperty(phoneId,
1355                TelephonyProperties.PROPERTY_OPERATOR_ISROAMING, null));
1356    }
1357
1358    /**
1359     * Returns the ISO country code equivalent of the current registered
1360     * operator's MCC (Mobile Country Code).
1361     * <p>
1362     * Availability: Only when user is registered to a network. Result may be
1363     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1364     * on a CDMA network).
1365     */
1366    public String getNetworkCountryIso() {
1367        return getNetworkCountryIsoForPhone(getDefaultPhone());
1368    }
1369
1370    /**
1371     * Returns the ISO country code equivalent of the current registered
1372     * operator's MCC (Mobile Country Code) of a subscription.
1373     * <p>
1374     * Availability: Only when user is registered to a network. Result may be
1375     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1376     * on a CDMA network).
1377     *
1378     * @param subId for which Network CountryIso is returned
1379     */
1380    public String getNetworkCountryIso(int subId) {
1381        int phoneId = SubscriptionManager.getPhoneId(subId);
1382        return getNetworkCountryIsoForPhone(phoneId);
1383    }
1384
1385    /**
1386     * Returns the ISO country code equivalent of the current registered
1387     * operator's MCC (Mobile Country Code) of a subscription.
1388     * <p>
1389     * Availability: Only when user is registered to a network. Result may be
1390     * unreliable on CDMA networks (use {@link #getPhoneType()} to determine if
1391     * on a CDMA network).
1392     *
1393     * @param phoneId for which Network CountryIso is returned
1394     */
1395    /** {@hide} */
1396    public String getNetworkCountryIsoForPhone(int phoneId) {
1397        return getTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_ISO_COUNTRY, "");
1398    }
1399
1400    /** Network type is unknown */
1401    public static final int NETWORK_TYPE_UNKNOWN = 0;
1402    /** Current network is GPRS */
1403    public static final int NETWORK_TYPE_GPRS = 1;
1404    /** Current network is EDGE */
1405    public static final int NETWORK_TYPE_EDGE = 2;
1406    /** Current network is UMTS */
1407    public static final int NETWORK_TYPE_UMTS = 3;
1408    /** Current network is CDMA: Either IS95A or IS95B*/
1409    public static final int NETWORK_TYPE_CDMA = 4;
1410    /** Current network is EVDO revision 0*/
1411    public static final int NETWORK_TYPE_EVDO_0 = 5;
1412    /** Current network is EVDO revision A*/
1413    public static final int NETWORK_TYPE_EVDO_A = 6;
1414    /** Current network is 1xRTT*/
1415    public static final int NETWORK_TYPE_1xRTT = 7;
1416    /** Current network is HSDPA */
1417    public static final int NETWORK_TYPE_HSDPA = 8;
1418    /** Current network is HSUPA */
1419    public static final int NETWORK_TYPE_HSUPA = 9;
1420    /** Current network is HSPA */
1421    public static final int NETWORK_TYPE_HSPA = 10;
1422    /** Current network is iDen */
1423    public static final int NETWORK_TYPE_IDEN = 11;
1424    /** Current network is EVDO revision B*/
1425    public static final int NETWORK_TYPE_EVDO_B = 12;
1426    /** Current network is LTE */
1427    public static final int NETWORK_TYPE_LTE = 13;
1428    /** Current network is eHRPD */
1429    public static final int NETWORK_TYPE_EHRPD = 14;
1430    /** Current network is HSPA+ */
1431    public static final int NETWORK_TYPE_HSPAP = 15;
1432    /** Current network is GSM {@hide} */
1433    public static final int NETWORK_TYPE_GSM = 16;
1434     /** Current network is TD_SCDMA {@hide} */
1435    public static final int NETWORK_TYPE_TD_SCDMA = 17;
1436   /** Current network is IWLAN {@hide} */
1437    public static final int NETWORK_TYPE_IWLAN = 18;
1438
1439    /**
1440     * @return the NETWORK_TYPE_xxxx for current data connection.
1441     */
1442    public int getNetworkType() {
1443       try {
1444           ITelephony telephony = getITelephony();
1445           if (telephony != null) {
1446               return telephony.getNetworkType();
1447            } else {
1448                // This can happen when the ITelephony interface is not up yet.
1449                return NETWORK_TYPE_UNKNOWN;
1450            }
1451        } catch(RemoteException ex) {
1452            // This shouldn't happen in the normal case
1453            return NETWORK_TYPE_UNKNOWN;
1454        } catch (NullPointerException ex) {
1455            // This could happen before phone restarts due to crashing
1456            return NETWORK_TYPE_UNKNOWN;
1457        }
1458    }
1459
1460    /**
1461     * Returns a constant indicating the radio technology (network type)
1462     * currently in use on the device for a subscription.
1463     * @return the network type
1464     *
1465     * @param subId for which network type is returned
1466     *
1467     * @see #NETWORK_TYPE_UNKNOWN
1468     * @see #NETWORK_TYPE_GPRS
1469     * @see #NETWORK_TYPE_EDGE
1470     * @see #NETWORK_TYPE_UMTS
1471     * @see #NETWORK_TYPE_HSDPA
1472     * @see #NETWORK_TYPE_HSUPA
1473     * @see #NETWORK_TYPE_HSPA
1474     * @see #NETWORK_TYPE_CDMA
1475     * @see #NETWORK_TYPE_EVDO_0
1476     * @see #NETWORK_TYPE_EVDO_A
1477     * @see #NETWORK_TYPE_EVDO_B
1478     * @see #NETWORK_TYPE_1xRTT
1479     * @see #NETWORK_TYPE_IDEN
1480     * @see #NETWORK_TYPE_LTE
1481     * @see #NETWORK_TYPE_EHRPD
1482     * @see #NETWORK_TYPE_HSPAP
1483     *
1484     * <p>
1485     * Requires Permission:
1486     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1487     */
1488   public int getNetworkType(int subId) {
1489       try {
1490           ITelephony telephony = getITelephony();
1491           if (telephony != null) {
1492               return telephony.getNetworkTypeForSubscriber(subId, getOpPackageName());
1493           } else {
1494               // This can happen when the ITelephony interface is not up yet.
1495               return NETWORK_TYPE_UNKNOWN;
1496           }
1497       } catch(RemoteException ex) {
1498           // This shouldn't happen in the normal case
1499           return NETWORK_TYPE_UNKNOWN;
1500       } catch (NullPointerException ex) {
1501           // This could happen before phone restarts due to crashing
1502           return NETWORK_TYPE_UNKNOWN;
1503       }
1504   }
1505
1506    /**
1507     * Returns a constant indicating the radio technology (network type)
1508     * currently in use on the device for data transmission.
1509     * @return the network type
1510     *
1511     * @see #NETWORK_TYPE_UNKNOWN
1512     * @see #NETWORK_TYPE_GPRS
1513     * @see #NETWORK_TYPE_EDGE
1514     * @see #NETWORK_TYPE_UMTS
1515     * @see #NETWORK_TYPE_HSDPA
1516     * @see #NETWORK_TYPE_HSUPA
1517     * @see #NETWORK_TYPE_HSPA
1518     * @see #NETWORK_TYPE_CDMA
1519     * @see #NETWORK_TYPE_EVDO_0
1520     * @see #NETWORK_TYPE_EVDO_A
1521     * @see #NETWORK_TYPE_EVDO_B
1522     * @see #NETWORK_TYPE_1xRTT
1523     * @see #NETWORK_TYPE_IDEN
1524     * @see #NETWORK_TYPE_LTE
1525     * @see #NETWORK_TYPE_EHRPD
1526     * @see #NETWORK_TYPE_HSPAP
1527     *
1528     * <p>
1529     * Requires Permission:
1530     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1531     * @hide
1532     */
1533    public int getDataNetworkType() {
1534        return getDataNetworkType(getDefaultSubscription());
1535    }
1536
1537    /**
1538     * Returns a constant indicating the radio technology (network type)
1539     * currently in use on the device for data transmission for a subscription
1540     * @return the network type
1541     *
1542     * @param subId for which network type is returned
1543     *
1544     * <p>
1545     * Requires Permission:
1546     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1547     */
1548    public int getDataNetworkType(int subId) {
1549        try{
1550            ITelephony telephony = getITelephony();
1551            if (telephony != null) {
1552                return telephony.getDataNetworkTypeForSubscriber(subId, getOpPackageName());
1553            } else {
1554                // This can happen when the ITelephony interface is not up yet.
1555                return NETWORK_TYPE_UNKNOWN;
1556            }
1557        } catch(RemoteException ex) {
1558            // This shouldn't happen in the normal case
1559            return NETWORK_TYPE_UNKNOWN;
1560        } catch (NullPointerException ex) {
1561            // This could happen before phone restarts due to crashing
1562            return NETWORK_TYPE_UNKNOWN;
1563        }
1564    }
1565
1566    /**
1567     * Returns the NETWORK_TYPE_xxxx for voice
1568     *
1569     * <p>
1570     * Requires Permission:
1571     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1572     * @hide
1573     */
1574    public int getVoiceNetworkType() {
1575        return getVoiceNetworkType(getDefaultSubscription());
1576    }
1577
1578    /**
1579     * Returns the NETWORK_TYPE_xxxx for voice for a subId
1580     *
1581     * <p>
1582     * Requires Permission:
1583     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1584     */
1585    public int getVoiceNetworkType(int subId) {
1586        try{
1587            ITelephony telephony = getITelephony();
1588            if (telephony != null) {
1589                return telephony.getVoiceNetworkTypeForSubscriber(subId, getOpPackageName());
1590            } else {
1591                // This can happen when the ITelephony interface is not up yet.
1592                return NETWORK_TYPE_UNKNOWN;
1593            }
1594        } catch(RemoteException ex) {
1595            // This shouldn't happen in the normal case
1596            return NETWORK_TYPE_UNKNOWN;
1597        } catch (NullPointerException ex) {
1598            // This could happen before phone restarts due to crashing
1599            return NETWORK_TYPE_UNKNOWN;
1600        }
1601    }
1602
1603    /** Unknown network class. {@hide} */
1604    public static final int NETWORK_CLASS_UNKNOWN = 0;
1605    /** Class of broadly defined "2G" networks. {@hide} */
1606    public static final int NETWORK_CLASS_2_G = 1;
1607    /** Class of broadly defined "3G" networks. {@hide} */
1608    public static final int NETWORK_CLASS_3_G = 2;
1609    /** Class of broadly defined "4G" networks. {@hide} */
1610    public static final int NETWORK_CLASS_4_G = 3;
1611
1612    /**
1613     * Return general class of network type, such as "3G" or "4G". In cases
1614     * where classification is contentious, this method is conservative.
1615     *
1616     * @hide
1617     */
1618    public static int getNetworkClass(int networkType) {
1619        switch (networkType) {
1620            case NETWORK_TYPE_GPRS:
1621            case NETWORK_TYPE_GSM:
1622            case NETWORK_TYPE_EDGE:
1623            case NETWORK_TYPE_CDMA:
1624            case NETWORK_TYPE_1xRTT:
1625            case NETWORK_TYPE_IDEN:
1626                return NETWORK_CLASS_2_G;
1627            case NETWORK_TYPE_UMTS:
1628            case NETWORK_TYPE_EVDO_0:
1629            case NETWORK_TYPE_EVDO_A:
1630            case NETWORK_TYPE_HSDPA:
1631            case NETWORK_TYPE_HSUPA:
1632            case NETWORK_TYPE_HSPA:
1633            case NETWORK_TYPE_EVDO_B:
1634            case NETWORK_TYPE_EHRPD:
1635            case NETWORK_TYPE_HSPAP:
1636            case NETWORK_TYPE_TD_SCDMA:
1637                return NETWORK_CLASS_3_G;
1638            case NETWORK_TYPE_LTE:
1639            case NETWORK_TYPE_IWLAN:
1640                return NETWORK_CLASS_4_G;
1641            default:
1642                return NETWORK_CLASS_UNKNOWN;
1643        }
1644    }
1645
1646    /**
1647     * Returns a string representation of the radio technology (network type)
1648     * currently in use on the device.
1649     * @return the name of the radio technology
1650     *
1651     * @hide pending API council review
1652     */
1653    public String getNetworkTypeName() {
1654        return getNetworkTypeName(getNetworkType());
1655    }
1656
1657    /**
1658     * Returns a string representation of the radio technology (network type)
1659     * currently in use on the device.
1660     * @param subId for which network type is returned
1661     * @return the name of the radio technology
1662     *
1663     */
1664    /** {@hide} */
1665    public static String getNetworkTypeName(int type) {
1666        switch (type) {
1667            case NETWORK_TYPE_GPRS:
1668                return "GPRS";
1669            case NETWORK_TYPE_EDGE:
1670                return "EDGE";
1671            case NETWORK_TYPE_UMTS:
1672                return "UMTS";
1673            case NETWORK_TYPE_HSDPA:
1674                return "HSDPA";
1675            case NETWORK_TYPE_HSUPA:
1676                return "HSUPA";
1677            case NETWORK_TYPE_HSPA:
1678                return "HSPA";
1679            case NETWORK_TYPE_CDMA:
1680                return "CDMA";
1681            case NETWORK_TYPE_EVDO_0:
1682                return "CDMA - EvDo rev. 0";
1683            case NETWORK_TYPE_EVDO_A:
1684                return "CDMA - EvDo rev. A";
1685            case NETWORK_TYPE_EVDO_B:
1686                return "CDMA - EvDo rev. B";
1687            case NETWORK_TYPE_1xRTT:
1688                return "CDMA - 1xRTT";
1689            case NETWORK_TYPE_LTE:
1690                return "LTE";
1691            case NETWORK_TYPE_EHRPD:
1692                return "CDMA - eHRPD";
1693            case NETWORK_TYPE_IDEN:
1694                return "iDEN";
1695            case NETWORK_TYPE_HSPAP:
1696                return "HSPA+";
1697            case NETWORK_TYPE_GSM:
1698                return "GSM";
1699            case NETWORK_TYPE_TD_SCDMA:
1700                return "TD_SCDMA";
1701            case NETWORK_TYPE_IWLAN:
1702                return "IWLAN";
1703            default:
1704                return "UNKNOWN";
1705        }
1706    }
1707
1708    //
1709    //
1710    // SIM Card
1711    //
1712    //
1713
1714    /**
1715     * SIM card state: Unknown. Signifies that the SIM is in transition
1716     * between states. For example, when the user inputs the SIM pin
1717     * under PIN_REQUIRED state, a query for sim status returns
1718     * this state before turning to SIM_STATE_READY.
1719     *
1720     * These are the ordinal value of IccCardConstants.State.
1721     */
1722    public static final int SIM_STATE_UNKNOWN = 0;
1723    /** SIM card state: no SIM card is available in the device */
1724    public static final int SIM_STATE_ABSENT = 1;
1725    /** SIM card state: Locked: requires the user's SIM PIN to unlock */
1726    public static final int SIM_STATE_PIN_REQUIRED = 2;
1727    /** SIM card state: Locked: requires the user's SIM PUK to unlock */
1728    public static final int SIM_STATE_PUK_REQUIRED = 3;
1729    /** SIM card state: Locked: requires a network PIN to unlock */
1730    public static final int SIM_STATE_NETWORK_LOCKED = 4;
1731    /** SIM card state: Ready */
1732    public static final int SIM_STATE_READY = 5;
1733    /** SIM card state: SIM Card is NOT READY
1734     *@hide
1735     */
1736    public static final int SIM_STATE_NOT_READY = 6;
1737    /** SIM card state: SIM Card Error, permanently disabled
1738     *@hide
1739     */
1740    public static final int SIM_STATE_PERM_DISABLED = 7;
1741    /** SIM card state: SIM Card Error, present but faulty
1742     *@hide
1743     */
1744    public static final int SIM_STATE_CARD_IO_ERROR = 8;
1745
1746    /**
1747     * @return true if a ICC card is present
1748     */
1749    public boolean hasIccCard() {
1750        return hasIccCard(getDefaultSim());
1751    }
1752
1753    /**
1754     * @return true if a ICC card is present for a subscription
1755     *
1756     * @param slotId for which icc card presence is checked
1757     */
1758    /** {@hide} */
1759    // FIXME Input argument slotId should be of type int
1760    public boolean hasIccCard(int slotId) {
1761
1762        try {
1763            ITelephony telephony = getITelephony();
1764            if (telephony == null)
1765                return false;
1766            return telephony.hasIccCardUsingSlotId(slotId);
1767        } catch (RemoteException ex) {
1768            // Assume no ICC card if remote exception which shouldn't happen
1769            return false;
1770        } catch (NullPointerException ex) {
1771            // This could happen before phone restarts due to crashing
1772            return false;
1773        }
1774    }
1775
1776    /**
1777     * Returns a constant indicating the state of the default SIM card.
1778     *
1779     * @see #SIM_STATE_UNKNOWN
1780     * @see #SIM_STATE_ABSENT
1781     * @see #SIM_STATE_PIN_REQUIRED
1782     * @see #SIM_STATE_PUK_REQUIRED
1783     * @see #SIM_STATE_NETWORK_LOCKED
1784     * @see #SIM_STATE_READY
1785     * @see #SIM_STATE_NOT_READY
1786     * @see #SIM_STATE_PERM_DISABLED
1787     * @see #SIM_STATE_CARD_IO_ERROR
1788     */
1789    public int getSimState() {
1790        int slotIdx = getDefaultSim();
1791        // slotIdx may be invalid due to sim being absent. In that case query all slots to get
1792        // sim state
1793        if (slotIdx < 0) {
1794            // query for all slots and return absent if all sim states are absent, otherwise
1795            // return unknown
1796            for (int i = 0; i < getPhoneCount(); i++) {
1797                int simState = getSimState(i);
1798                if (simState != SIM_STATE_ABSENT) {
1799                    Rlog.d(TAG, "getSimState: default sim:" + slotIdx + ", sim state for " +
1800                            "slotIdx=" + i + " is " + simState + ", return state as unknown");
1801                    return SIM_STATE_UNKNOWN;
1802                }
1803            }
1804            Rlog.d(TAG, "getSimState: default sim:" + slotIdx + ", all SIMs absent, return " +
1805                    "state as absent");
1806            return SIM_STATE_ABSENT;
1807        }
1808        return getSimState(slotIdx);
1809    }
1810
1811    /**
1812     * Returns a constant indicating the state of the device SIM card in a slot.
1813     *
1814     * @param slotIdx
1815     *
1816     * @see #SIM_STATE_UNKNOWN
1817     * @see #SIM_STATE_ABSENT
1818     * @see #SIM_STATE_PIN_REQUIRED
1819     * @see #SIM_STATE_PUK_REQUIRED
1820     * @see #SIM_STATE_NETWORK_LOCKED
1821     * @see #SIM_STATE_READY
1822     * @see #SIM_STATE_NOT_READY
1823     * @see #SIM_STATE_PERM_DISABLED
1824     * @see #SIM_STATE_CARD_IO_ERROR
1825     */
1826    /** {@hide} */
1827    public int getSimState(int slotIdx) {
1828        int simState = SubscriptionManager.getSimStateForSlotIdx(slotIdx);
1829        return simState;
1830    }
1831
1832    /**
1833     * Returns the MCC+MNC (mobile country code + mobile network code) of the
1834     * provider of the SIM. 5 or 6 decimal digits.
1835     * <p>
1836     * Availability: SIM state must be {@link #SIM_STATE_READY}
1837     *
1838     * @see #getSimState
1839     */
1840    public String getSimOperator() {
1841        return getSimOperatorNumeric();
1842    }
1843
1844    /**
1845     * Returns the MCC+MNC (mobile country code + mobile network code) of the
1846     * provider of the SIM. 5 or 6 decimal digits.
1847     * <p>
1848     * Availability: SIM state must be {@link #SIM_STATE_READY}
1849     *
1850     * @see #getSimState
1851     *
1852     * @param subId for which SimOperator is returned
1853     */
1854    public String getSimOperator(int subId) {
1855        return getSimOperatorNumeric(subId);
1856    }
1857
1858    /**
1859     * Returns the MCC+MNC (mobile country code + mobile network code) of the
1860     * provider of the SIM. 5 or 6 decimal digits.
1861     * <p>
1862     * Availability: SIM state must be {@link #SIM_STATE_READY}
1863     *
1864     * @see #getSimState
1865     * @hide
1866     */
1867    public String getSimOperatorNumeric() {
1868        int subId = SubscriptionManager.getDefaultDataSubscriptionId();
1869        if (!SubscriptionManager.isUsableSubIdValue(subId)) {
1870            subId = SubscriptionManager.getDefaultSmsSubscriptionId();
1871            if (!SubscriptionManager.isUsableSubIdValue(subId)) {
1872                subId = SubscriptionManager.getDefaultVoiceSubscriptionId();
1873                if (!SubscriptionManager.isUsableSubIdValue(subId)) {
1874                    subId = SubscriptionManager.getDefaultSubscriptionId();
1875                }
1876            }
1877        }
1878        return getSimOperatorNumeric(subId);
1879    }
1880
1881    /**
1882     * Returns the MCC+MNC (mobile country code + mobile network code) of the
1883     * provider of the SIM for a particular subscription. 5 or 6 decimal digits.
1884     * <p>
1885     * Availability: SIM state must be {@link #SIM_STATE_READY}
1886     *
1887     * @see #getSimState
1888     *
1889     * @param subId for which SimOperator is returned
1890     * @hide
1891     */
1892    public String getSimOperatorNumeric(int subId) {
1893        int phoneId = SubscriptionManager.getPhoneId(subId);
1894        return getSimOperatorNumericForPhone(phoneId);
1895    }
1896
1897    /**
1898     * Returns the MCC+MNC (mobile country code + mobile network code) of the
1899     * provider of the SIM for a particular subscription. 5 or 6 decimal digits.
1900     * <p>
1901     *
1902     * @param phoneId for which SimOperator is returned
1903     * @hide
1904     */
1905    public String getSimOperatorNumericForPhone(int phoneId) {
1906        return getTelephonyProperty(phoneId,
1907                TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC, "");
1908    }
1909
1910    /**
1911     * Returns the Service Provider Name (SPN).
1912     * <p>
1913     * Availability: SIM state must be {@link #SIM_STATE_READY}
1914     *
1915     * @see #getSimState
1916     */
1917    public String getSimOperatorName() {
1918        return getSimOperatorNameForPhone(getDefaultPhone());
1919    }
1920
1921    /**
1922     * Returns the Service Provider Name (SPN).
1923     * <p>
1924     * Availability: SIM state must be {@link #SIM_STATE_READY}
1925     *
1926     * @see #getSimState
1927     *
1928     * @param subId for which SimOperatorName is returned
1929     */
1930    public String getSimOperatorName(int subId) {
1931        int phoneId = SubscriptionManager.getPhoneId(subId);
1932        return getSimOperatorNameForPhone(phoneId);
1933    }
1934
1935    /**
1936     * Returns the Service Provider Name (SPN).
1937     *
1938     * @hide
1939     */
1940    public String getSimOperatorNameForPhone(int phoneId) {
1941         return getTelephonyProperty(phoneId,
1942                TelephonyProperties.PROPERTY_ICC_OPERATOR_ALPHA, "");
1943    }
1944
1945    /**
1946     * Returns the ISO country code equivalent for the SIM provider's country code.
1947     */
1948    public String getSimCountryIso() {
1949        return getSimCountryIsoForPhone(getDefaultPhone());
1950    }
1951
1952    /**
1953     * Returns the ISO country code equivalent for the SIM provider's country code.
1954     *
1955     * @param subId for which SimCountryIso is returned
1956     */
1957    public String getSimCountryIso(int subId) {
1958        int phoneId = SubscriptionManager.getPhoneId(subId);
1959        return getSimCountryIsoForPhone(phoneId);
1960    }
1961
1962    /**
1963     * Returns the ISO country code equivalent for the SIM provider's country code.
1964     *
1965     * @hide
1966     */
1967    public String getSimCountryIsoForPhone(int phoneId) {
1968        return getTelephonyProperty(phoneId,
1969                TelephonyProperties.PROPERTY_ICC_OPERATOR_ISO_COUNTRY, "");
1970    }
1971
1972    /**
1973     * Returns the serial number of the SIM, if applicable. Return null if it is
1974     * unavailable.
1975     * <p>
1976     * Requires Permission:
1977     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1978     */
1979    public String getSimSerialNumber() {
1980         return getSimSerialNumber(getDefaultSubscription());
1981    }
1982
1983    /**
1984     * Returns the serial number for the given subscription, if applicable. Return null if it is
1985     * unavailable.
1986     * <p>
1987     * @param subId for which Sim Serial number is returned
1988     * Requires Permission:
1989     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
1990     */
1991    public String getSimSerialNumber(int subId) {
1992        try {
1993            IPhoneSubInfo info = getSubscriberInfo();
1994            if (info == null)
1995                return null;
1996            return info.getIccSerialNumberForSubscriber(subId, mContext.getOpPackageName());
1997        } catch (RemoteException ex) {
1998            return null;
1999        } catch (NullPointerException ex) {
2000            // This could happen before phone restarts due to crashing
2001            return null;
2002        }
2003    }
2004
2005    /**
2006     * Return if the current radio is LTE on CDMA. This
2007     * is a tri-state return value as for a period of time
2008     * the mode may be unknown.
2009     *
2010     * @return {@link PhoneConstants#LTE_ON_CDMA_UNKNOWN}, {@link PhoneConstants#LTE_ON_CDMA_FALSE}
2011     * or {@link PhoneConstants#LTE_ON_CDMA_TRUE}
2012     *
2013     * <p>
2014     * Requires Permission:
2015     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2016     *
2017     * @hide
2018     */
2019    public int getLteOnCdmaMode() {
2020        return getLteOnCdmaMode(getDefaultSubscription());
2021    }
2022
2023    /**
2024     * Return if the current radio is LTE on CDMA for Subscription. This
2025     * is a tri-state return value as for a period of time
2026     * the mode may be unknown.
2027     *
2028     * @param subId for which radio is LTE on CDMA is returned
2029     * @return {@link PhoneConstants#LTE_ON_CDMA_UNKNOWN}, {@link PhoneConstants#LTE_ON_CDMA_FALSE}
2030     * or {@link PhoneConstants#LTE_ON_CDMA_TRUE}
2031     *
2032     * <p>
2033     * Requires Permission:
2034     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2035     */
2036    /** {@hide} */
2037    public int getLteOnCdmaMode(int subId) {
2038        try {
2039            ITelephony telephony = getITelephony();
2040            if (telephony == null)
2041                return PhoneConstants.LTE_ON_CDMA_UNKNOWN;
2042            return telephony.getLteOnCdmaModeForSubscriber(subId, getOpPackageName());
2043        } catch (RemoteException ex) {
2044            // Assume no ICC card if remote exception which shouldn't happen
2045            return PhoneConstants.LTE_ON_CDMA_UNKNOWN;
2046        } catch (NullPointerException ex) {
2047            // This could happen before phone restarts due to crashing
2048            return PhoneConstants.LTE_ON_CDMA_UNKNOWN;
2049        }
2050    }
2051
2052    //
2053    //
2054    // Subscriber Info
2055    //
2056    //
2057
2058    /**
2059     * Returns the unique subscriber ID, for example, the IMSI for a GSM phone.
2060     * Return null if it is unavailable.
2061     * <p>
2062     * Requires Permission:
2063     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2064     */
2065    public String getSubscriberId() {
2066        return getSubscriberId(getDefaultSubscription());
2067    }
2068
2069    /**
2070     * Returns the unique subscriber ID, for example, the IMSI for a GSM phone
2071     * for a subscription.
2072     * Return null if it is unavailable.
2073     * <p>
2074     * Requires Permission:
2075     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2076     *
2077     * @param subId whose subscriber id is returned
2078     */
2079    public String getSubscriberId(int subId) {
2080        try {
2081            IPhoneSubInfo info = getSubscriberInfo();
2082            if (info == null)
2083                return null;
2084            return info.getSubscriberIdForSubscriber(subId, mContext.getOpPackageName());
2085        } catch (RemoteException ex) {
2086            return null;
2087        } catch (NullPointerException ex) {
2088            // This could happen before phone restarts due to crashing
2089            return null;
2090        }
2091    }
2092
2093    /**
2094     * Returns the Group Identifier Level1 for a GSM phone.
2095     * Return null if it is unavailable.
2096     * <p>
2097     * Requires Permission:
2098     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2099     */
2100    public String getGroupIdLevel1() {
2101        try {
2102            IPhoneSubInfo info = getSubscriberInfo();
2103            if (info == null)
2104                return null;
2105            return info.getGroupIdLevel1(mContext.getOpPackageName());
2106        } catch (RemoteException ex) {
2107            return null;
2108        } catch (NullPointerException ex) {
2109            // This could happen before phone restarts due to crashing
2110            return null;
2111        }
2112    }
2113
2114    /**
2115     * Returns the Group Identifier Level1 for a GSM phone for a particular subscription.
2116     * Return null if it is unavailable.
2117     * <p>
2118     * Requires Permission:
2119     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2120     *
2121     * @param subId whose subscriber id is returned
2122     */
2123    public String getGroupIdLevel1(int subId) {
2124        try {
2125            IPhoneSubInfo info = getSubscriberInfo();
2126            if (info == null)
2127                return null;
2128            return info.getGroupIdLevel1ForSubscriber(subId, mContext.getOpPackageName());
2129        } catch (RemoteException ex) {
2130            return null;
2131        } catch (NullPointerException ex) {
2132            // This could happen before phone restarts due to crashing
2133            return null;
2134        }
2135    }
2136
2137    /**
2138     * Returns the phone number string for line 1, for example, the MSISDN
2139     * for a GSM phone. Return null if it is unavailable.
2140     * <p>
2141     * Requires Permission:
2142     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2143     *   OR
2144     *   {@link android.Manifest.permission#READ_SMS}
2145     * <p>
2146     * The default SMS app can also use this.
2147     */
2148    public String getLine1Number() {
2149        return getLine1Number(getDefaultSubscription());
2150    }
2151
2152    /**
2153     * Returns the phone number string for line 1, for example, the MSISDN
2154     * for a GSM phone for a particular subscription. Return null if it is unavailable.
2155     * <p>
2156     * Requires Permission:
2157     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2158     *   OR
2159     *   {@link android.Manifest.permission#READ_SMS}
2160     * <p>
2161     * The default SMS app can also use this.
2162     *
2163     * @param subId whose phone number for line 1 is returned
2164     */
2165    public String getLine1Number(int subId) {
2166        String number = null;
2167        try {
2168            ITelephony telephony = getITelephony();
2169            if (telephony != null)
2170                number = telephony.getLine1NumberForDisplay(subId, mContext.getOpPackageName());
2171        } catch (RemoteException ex) {
2172        } catch (NullPointerException ex) {
2173        }
2174        if (number != null) {
2175            return number;
2176        }
2177        try {
2178            IPhoneSubInfo info = getSubscriberInfo();
2179            if (info == null)
2180                return null;
2181            return info.getLine1NumberForSubscriber(subId, mContext.getOpPackageName());
2182        } catch (RemoteException ex) {
2183            return null;
2184        } catch (NullPointerException ex) {
2185            // This could happen before phone restarts due to crashing
2186            return null;
2187        }
2188    }
2189
2190    /**
2191     * Set the line 1 phone number string and its alphatag for the current ICCID
2192     * for display purpose only, for example, displayed in Phone Status. It won't
2193     * change the actual MSISDN/MDN. To unset alphatag or number, pass in a null
2194     * value.
2195     *
2196     * <p>Requires that the calling app has carrier privileges.
2197     * @see #hasCarrierPrivileges
2198     *
2199     * @param alphaTag alpha-tagging of the dailing nubmer
2200     * @param number The dialing number
2201     * @return true if the operation was executed correctly.
2202     */
2203    public boolean setLine1NumberForDisplay(String alphaTag, String number) {
2204        return setLine1NumberForDisplay(getDefaultSubscription(), alphaTag, number);
2205    }
2206
2207    /**
2208     * Set the line 1 phone number string and its alphatag for the current ICCID
2209     * for display purpose only, for example, displayed in Phone Status. It won't
2210     * change the actual MSISDN/MDN. To unset alphatag or number, pass in a null
2211     * value.
2212     *
2213     * <p>Requires that the calling app has carrier privileges.
2214     * @see #hasCarrierPrivileges
2215     *
2216     * @param subId the subscriber that the alphatag and dialing number belongs to.
2217     * @param alphaTag alpha-tagging of the dailing nubmer
2218     * @param number The dialing number
2219     * @return true if the operation was executed correctly.
2220     */
2221    public boolean setLine1NumberForDisplay(int subId, String alphaTag, String number) {
2222        try {
2223            ITelephony telephony = getITelephony();
2224            if (telephony != null)
2225                return telephony.setLine1NumberForDisplayForSubscriber(subId, alphaTag, number);
2226        } catch (RemoteException ex) {
2227        } catch (NullPointerException ex) {
2228        }
2229        return false;
2230    }
2231
2232    /**
2233     * Returns the alphabetic identifier associated with the line 1 number.
2234     * Return null if it is unavailable.
2235     * <p>
2236     * Requires Permission:
2237     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2238     * @hide
2239     * nobody seems to call this.
2240     */
2241    public String getLine1AlphaTag() {
2242        return getLine1AlphaTag(getDefaultSubscription());
2243    }
2244
2245    /**
2246     * Returns the alphabetic identifier associated with the line 1 number
2247     * for a subscription.
2248     * Return null if it is unavailable.
2249     * <p>
2250     * Requires Permission:
2251     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2252     * @param subId whose alphabetic identifier associated with line 1 is returned
2253     * nobody seems to call this.
2254     */
2255    public String getLine1AlphaTag(int subId) {
2256        String alphaTag = null;
2257        try {
2258            ITelephony telephony = getITelephony();
2259            if (telephony != null)
2260                alphaTag = telephony.getLine1AlphaTagForDisplay(subId,
2261                        getOpPackageName());
2262        } catch (RemoteException ex) {
2263        } catch (NullPointerException ex) {
2264        }
2265        if (alphaTag != null) {
2266            return alphaTag;
2267        }
2268        try {
2269            IPhoneSubInfo info = getSubscriberInfo();
2270            if (info == null)
2271                return null;
2272            return info.getLine1AlphaTagForSubscriber(subId, getOpPackageName());
2273        } catch (RemoteException ex) {
2274            return null;
2275        } catch (NullPointerException ex) {
2276            // This could happen before phone restarts due to crashing
2277            return null;
2278        }
2279    }
2280
2281    /**
2282     * Return the set of subscriber IDs that should be considered as "merged
2283     * together" for data usage purposes. This is commonly {@code null} to
2284     * indicate no merging is required. Any returned subscribers are sorted in a
2285     * deterministic order.
2286     *
2287     * @hide
2288     */
2289    public @Nullable String[] getMergedSubscriberIds() {
2290        try {
2291            ITelephony telephony = getITelephony();
2292            if (telephony != null)
2293                return telephony.getMergedSubscriberIds(getOpPackageName());
2294        } catch (RemoteException ex) {
2295        } catch (NullPointerException ex) {
2296        }
2297        return null;
2298    }
2299
2300    /**
2301     * Returns the MSISDN string.
2302     * for a GSM phone. Return null if it is unavailable.
2303     * <p>
2304     * Requires Permission:
2305     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2306     *
2307     * @hide
2308     */
2309    public String getMsisdn() {
2310        return getMsisdn(getDefaultSubscription());
2311    }
2312
2313    /**
2314     * Returns the MSISDN string.
2315     * for a GSM phone. Return null if it is unavailable.
2316     * <p>
2317     * Requires Permission:
2318     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2319     *
2320     * @param subId for which msisdn is returned
2321     */
2322    /** {@hide} */
2323    public String getMsisdn(int subId) {
2324        try {
2325            IPhoneSubInfo info = getSubscriberInfo();
2326            if (info == null)
2327                return null;
2328            return info.getMsisdnForSubscriber(subId, getOpPackageName());
2329        } catch (RemoteException ex) {
2330            return null;
2331        } catch (NullPointerException ex) {
2332            // This could happen before phone restarts due to crashing
2333            return null;
2334        }
2335    }
2336
2337    /**
2338     * Returns the voice mail number. Return null if it is unavailable.
2339     * <p>
2340     * Requires Permission:
2341     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2342     */
2343    public String getVoiceMailNumber() {
2344        return getVoiceMailNumber(getDefaultSubscription());
2345    }
2346
2347    /**
2348     * Returns the voice mail number for a subscription.
2349     * Return null if it is unavailable.
2350     * <p>
2351     * Requires Permission:
2352     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2353     * @param subId whose voice mail number is returned
2354     */
2355    public String getVoiceMailNumber(int subId) {
2356        try {
2357            IPhoneSubInfo info = getSubscriberInfo();
2358            if (info == null)
2359                return null;
2360            return info.getVoiceMailNumberForSubscriber(subId, getOpPackageName());
2361        } catch (RemoteException ex) {
2362            return null;
2363        } catch (NullPointerException ex) {
2364            // This could happen before phone restarts due to crashing
2365            return null;
2366        }
2367    }
2368
2369    /**
2370     * Returns the complete voice mail number. Return null if it is unavailable.
2371     * <p>
2372     * Requires Permission:
2373     *   {@link android.Manifest.permission#CALL_PRIVILEGED CALL_PRIVILEGED}
2374     *
2375     * @hide
2376     */
2377    public String getCompleteVoiceMailNumber() {
2378        return getCompleteVoiceMailNumber(getDefaultSubscription());
2379    }
2380
2381    /**
2382     * Returns the complete voice mail number. Return null if it is unavailable.
2383     * <p>
2384     * Requires Permission:
2385     *   {@link android.Manifest.permission#CALL_PRIVILEGED CALL_PRIVILEGED}
2386     *
2387     * @param subId
2388     */
2389    /** {@hide} */
2390    public String getCompleteVoiceMailNumber(int subId) {
2391        try {
2392            IPhoneSubInfo info = getSubscriberInfo();
2393            if (info == null)
2394                return null;
2395            return info.getCompleteVoiceMailNumberForSubscriber(subId);
2396        } catch (RemoteException ex) {
2397            return null;
2398        } catch (NullPointerException ex) {
2399            // This could happen before phone restarts due to crashing
2400            return null;
2401        }
2402    }
2403
2404    /**
2405     * Sets the voice mail number.
2406     *
2407     * <p>Requires that the calling app has carrier privileges.
2408     * @see #hasCarrierPrivileges
2409     *
2410     * @param alphaTag The alpha tag to display.
2411     * @param number The voicemail number.
2412     */
2413    public boolean setVoiceMailNumber(String alphaTag, String number) {
2414        return setVoiceMailNumber(getDefaultSubscription(), alphaTag, number);
2415    }
2416
2417    /**
2418     * Sets the voicemail number for the given subscriber.
2419     *
2420     * <p>Requires that the calling app has carrier privileges.
2421     * @see #hasCarrierPrivileges
2422     *
2423     * @param subId The subscription id.
2424     * @param alphaTag The alpha tag to display.
2425     * @param number The voicemail number.
2426     */
2427    public boolean setVoiceMailNumber(int subId, String alphaTag, String number) {
2428        try {
2429            ITelephony telephony = getITelephony();
2430            if (telephony != null)
2431                return telephony.setVoiceMailNumber(subId, alphaTag, number);
2432        } catch (RemoteException ex) {
2433        } catch (NullPointerException ex) {
2434        }
2435        return false;
2436    }
2437
2438    /**
2439     * Enables or disables the visual voicemail SMS filter for a phone account. When the filter is
2440     * enabled, Incoming SMS messages matching the OMTP VVM SMS interface will be redirected to the
2441     * visual voicemail client with
2442     * {@link android.provider.VoicemailContract.ACTION_VOICEMAIL_SMS_RECEIVED}.
2443     * @see #setVisualVoicemailSmsFilterPrefix(int, String)
2444     * @see #setVisualVoicemailSmsFilterOriginatingNumbers(int, String[])
2445     * @see #setVisualVoicemailSmsFilterDestinationPort(int, int)
2446     *
2447     * <p>This takes effect only when the caller is the default dialer.
2448     *
2449     * @param subId The subscription id of the phone account.
2450     * @param value The new state of the filter
2451     */
2452    /** @hide */
2453    public void setVisualVoicemailSmsFilterEnabled(int subId, boolean value){
2454        try {
2455            ITelephony telephony = getITelephony();
2456            if (telephony != null)
2457                telephony.setVisualVoicemailSmsFilterEnabled(subId, value);
2458        } catch (RemoteException ex) {
2459        } catch (NullPointerException ex) {
2460        }
2461    }
2462
2463    /**
2464     * Returns whether the visual voicemail SMS filter is enabled for a phone account.
2465     *
2466     * @param packageName The visual voicemail client to read the settings from
2467     * @param subId The subscription id of the phone account.
2468     */
2469    /** @hide */
2470    public boolean isVisualVoicemailSmsFilterEnabled(String packageName, int subId){
2471        try {
2472            ITelephony telephony = getITelephony();
2473            if (telephony != null) {
2474                return telephony.isVisualVoicemailSmsFilterEnabled(packageName, subId);
2475            }
2476        } catch (RemoteException ex) {
2477        } catch (NullPointerException ex) {
2478        }
2479
2480        return false;
2481    }
2482
2483    /**
2484     * Sets the client prefix for the visual voicemail SMS filter of a phone account. The client
2485     * prefix will appear at the start of a visual voicemail SMS message, followed by a colon(:).
2486     *
2487     * <p>This takes effect only when the caller is the default dialer.
2488     *
2489     * @param subId The subscription id of the phone account.
2490     * @param prefix The client prefix
2491     */
2492    /** @hide */
2493    public void setVisualVoicemailSmsFilterClientPrefix(int subId, String prefix){
2494        try {
2495            ITelephony telephony = getITelephony();
2496            if (telephony != null) {
2497                telephony.setVisualVoicemailSmsFilterClientPrefix(subId, prefix);
2498            }
2499        } catch (RemoteException ex) {
2500        } catch (NullPointerException ex) {
2501        }
2502    }
2503
2504    /**
2505     * Returns the client prefix for the visual voicemail SMS filter of a phone account. The client
2506     * prefix will appear at the start of a visual voicemail SMS message, followed by a colon(:).
2507     *
2508     * @param packageName The visual voicemail client to read the settings from
2509     * @param subId The subscription id of the phone account.
2510     */
2511    /** @hide */
2512    public String getVisualVoicemailSmsFilterClientPrefix(String packageName, int subId){
2513        try {
2514            ITelephony telephony = getITelephony();
2515            if (telephony != null) {
2516                return telephony.getVisualVoicemailSmsFilterClientPrefix(packageName, subId);
2517            }
2518        } catch (RemoteException ex) {
2519        } catch (NullPointerException ex) {
2520        }
2521        return null;
2522    }
2523
2524    /**
2525     * Sets the originating number whitelist for the visual voicemail SMS filter of a phone
2526     * account. If the list is not null only the SMS messages from a number in the list can be
2527     * considered as a visual voicemail SMS. Otherwise, messages from any address will be
2528     * considered.
2529     *
2530     * <p>This takes effect only when the caller is the default dialer.
2531     *
2532     * @param subId The subscription id of the phone account.
2533     * @param numbers A array representing the white list, or null to disable number filtering.
2534     */
2535    /** @hide */
2536    public void setVisualVoicemailSmsFilterOriginatingNumbers(int subId,
2537            @Nullable String[] numbers) {
2538        try {
2539            ITelephony telephony = getITelephony();
2540            if (telephony != null) {
2541                telephony.setVisualVoicemailSmsFilterOriginatingNumbers(subId, numbers);
2542            }
2543        } catch (RemoteException ex) {
2544        } catch (NullPointerException ex) {
2545        }
2546    }
2547
2548    /**
2549     * Returns the originating number whitelist for the visual voicemail SMS filter of a phone
2550     * account. If the list is not null only the SMS messages from a number in the list can be
2551     * considered as a visual voicemail SMS. Otherwise, messages from any address will be
2552     * considered.
2553     *
2554     * @param packageName The visual voicemail client to read the settings from
2555     * @param subId The subscription id of the phone account.
2556     */
2557    /** @hide */
2558    public String[] getVisualVoicemailSmsFilterOriginatingNumbers(String packageName, int subId){
2559        try {
2560            ITelephony telephony = getITelephony();
2561            if (telephony != null) {
2562                return telephony.getVisualVoicemailSmsFilterOriginatingNumbers(packageName, subId);
2563            }
2564        } catch (RemoteException ex) {
2565        } catch (NullPointerException ex) {
2566        }
2567        return null;
2568    }
2569
2570    /**
2571     * Sets the destination port for the visual voicemail SMS filter of a phone
2572     * account.
2573     *
2574     * <p>This takes effect only when the caller is the default dialer.
2575     *
2576     * @param subId The subscription id of the phone account.
2577     * @param port The destination port, or {@link #VVM_SMS_FILTER_DESTINATION_PORT_ANY}, or
2578     * {@link #VVM_SMS_FILTER_DESTINATION_PORT_DATA_SMS}
2579     */
2580    /** @hide */
2581    public void setVisualVoicemailSmsFilterDestinationPort(int subId, int port){
2582        try {
2583            ITelephony telephony = getITelephony();
2584            if (telephony != null) {
2585                telephony.setVisualVoicemailSmsFilterDestinationPort(subId, port);
2586            }
2587        } catch (RemoteException ex) {
2588        } catch (NullPointerException ex) {
2589        }
2590    }
2591
2592    /**
2593     * Returns the destination port for the visual voicemail SMS filter of a phone
2594     * account.
2595     *
2596     * @param packageName The visual voicemail client to read the settings from
2597     * @param subId The subscription id of the phone account.
2598     * @returns port The destination port, or {@link #VVM_SMS_FILTER_DESTINATION_PORT_ANY}, or
2599     * {@link #VVM_SMS_FILTER_DESTINATION_PORT_DATA_SMS}
2600     */
2601    /** @hide */
2602    public int getVisualVoicemailSmsFilterDestinationPort(String packageName, int subId){
2603        try {
2604            ITelephony telephony = getITelephony();
2605            if (telephony != null) {
2606                return telephony.getVisualVoicemailSmsFilterDestinationPort(packageName, subId);
2607            }
2608        } catch (RemoteException ex) {
2609        } catch (NullPointerException ex) {
2610        }
2611        return VVM_SMS_FILTER_DESTINATION_PORT_ANY;
2612    }
2613    /**
2614     * Returns the voice mail count. Return 0 if unavailable, -1 if there are unread voice messages
2615     * but the count is unknown.
2616     * <p>
2617     * Requires Permission:
2618     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2619     * @hide
2620     */
2621    public int getVoiceMessageCount() {
2622        return getVoiceMessageCount(getDefaultSubscription());
2623    }
2624
2625    /**
2626     * Returns the voice mail count for a subscription. Return 0 if unavailable.
2627     * <p>
2628     * Requires Permission:
2629     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2630     * @param subId whose voice message count is returned
2631     */
2632    /** {@hide} */
2633    public int getVoiceMessageCount(int subId) {
2634        try {
2635            ITelephony telephony = getITelephony();
2636            if (telephony == null)
2637                return 0;
2638            return telephony.getVoiceMessageCountForSubscriber(subId);
2639        } catch (RemoteException ex) {
2640            return 0;
2641        } catch (NullPointerException ex) {
2642            // This could happen before phone restarts due to crashing
2643            return 0;
2644        }
2645    }
2646
2647    /**
2648     * Retrieves the alphabetic identifier associated with the voice
2649     * mail number.
2650     * <p>
2651     * Requires Permission:
2652     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2653     */
2654    public String getVoiceMailAlphaTag() {
2655        return getVoiceMailAlphaTag(getDefaultSubscription());
2656    }
2657
2658    /**
2659     * Retrieves the alphabetic identifier associated with the voice
2660     * mail number for a subscription.
2661     * <p>
2662     * Requires Permission:
2663     * {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2664     * @param subId whose alphabetic identifier associated with the
2665     * voice mail number is returned
2666     */
2667    public String getVoiceMailAlphaTag(int subId) {
2668        try {
2669            IPhoneSubInfo info = getSubscriberInfo();
2670            if (info == null)
2671                return null;
2672            return info.getVoiceMailAlphaTagForSubscriber(subId, getOpPackageName());
2673        } catch (RemoteException ex) {
2674            return null;
2675        } catch (NullPointerException ex) {
2676            // This could happen before phone restarts due to crashing
2677            return null;
2678        }
2679    }
2680
2681    /**
2682     * Returns the IMS private user identity (IMPI) that was loaded from the ISIM.
2683     * @return the IMPI, or null if not present or not loaded
2684     * @hide
2685     */
2686    public String getIsimImpi() {
2687        try {
2688            IPhoneSubInfo info = getSubscriberInfo();
2689            if (info == null)
2690                return null;
2691            return info.getIsimImpi();
2692        } catch (RemoteException ex) {
2693            return null;
2694        } catch (NullPointerException ex) {
2695            // This could happen before phone restarts due to crashing
2696            return null;
2697        }
2698    }
2699
2700    /**
2701     * Returns the IMS home network domain name that was loaded from the ISIM.
2702     * @return the IMS domain name, or null if not present or not loaded
2703     * @hide
2704     */
2705    public String getIsimDomain() {
2706        try {
2707            IPhoneSubInfo info = getSubscriberInfo();
2708            if (info == null)
2709                return null;
2710            return info.getIsimDomain();
2711        } catch (RemoteException ex) {
2712            return null;
2713        } catch (NullPointerException ex) {
2714            // This could happen before phone restarts due to crashing
2715            return null;
2716        }
2717    }
2718
2719    /**
2720     * Returns the IMS public user identities (IMPU) that were loaded from the ISIM.
2721     * @return an array of IMPU strings, with one IMPU per string, or null if
2722     *      not present or not loaded
2723     * @hide
2724     */
2725    public String[] getIsimImpu() {
2726        try {
2727            IPhoneSubInfo info = getSubscriberInfo();
2728            if (info == null)
2729                return null;
2730            return info.getIsimImpu();
2731        } catch (RemoteException ex) {
2732            return null;
2733        } catch (NullPointerException ex) {
2734            // This could happen before phone restarts due to crashing
2735            return null;
2736        }
2737    }
2738
2739   /**
2740    * @hide
2741    */
2742    private IPhoneSubInfo getSubscriberInfo() {
2743        // get it each time because that process crashes a lot
2744        return IPhoneSubInfo.Stub.asInterface(ServiceManager.getService("iphonesubinfo"));
2745    }
2746
2747    /** Device call state: No activity. */
2748    public static final int CALL_STATE_IDLE = 0;
2749    /** Device call state: Ringing. A new call arrived and is
2750     *  ringing or waiting. In the latter case, another call is
2751     *  already active. */
2752    public static final int CALL_STATE_RINGING = 1;
2753    /** Device call state: Off-hook. At least one call exists
2754      * that is dialing, active, or on hold, and no calls are ringing
2755      * or waiting. */
2756    public static final int CALL_STATE_OFFHOOK = 2;
2757
2758    /**
2759     * Returns one of the following constants that represents the current state of all
2760     * phone calls.
2761     *
2762     * {@link TelephonyManager#CALL_STATE_RINGING}
2763     * {@link TelephonyManager#CALL_STATE_OFFHOOK}
2764     * {@link TelephonyManager#CALL_STATE_IDLE}
2765     */
2766    public int getCallState() {
2767        try {
2768            ITelecomService telecom = getTelecomService();
2769            if (telecom != null) {
2770                return telecom.getCallState();
2771            }
2772        } catch (RemoteException e) {
2773            Log.e(TAG, "Error calling ITelecomService#getCallState", e);
2774        }
2775        return CALL_STATE_IDLE;
2776    }
2777
2778    /**
2779     * Returns a constant indicating the call state (cellular) on the device
2780     * for a subscription.
2781     *
2782     * @param subId whose call state is returned
2783     */
2784    public int getCallState(int subId) {
2785        int phoneId = SubscriptionManager.getPhoneId(subId);
2786        return getCallStateForSlot(phoneId);
2787    }
2788
2789    /**
2790     * See getCallState.
2791     *
2792     * @hide
2793     */
2794    public int getCallStateForSlot(int slotId) {
2795        try {
2796            ITelephony telephony = getITelephony();
2797            if (telephony == null)
2798                return CALL_STATE_IDLE;
2799            return telephony.getCallStateForSlot(slotId);
2800        } catch (RemoteException ex) {
2801            // the phone process is restarting.
2802            return CALL_STATE_IDLE;
2803        } catch (NullPointerException ex) {
2804          // the phone process is restarting.
2805          return CALL_STATE_IDLE;
2806        }
2807    }
2808
2809
2810    /** Data connection activity: No traffic. */
2811    public static final int DATA_ACTIVITY_NONE = 0x00000000;
2812    /** Data connection activity: Currently receiving IP PPP traffic. */
2813    public static final int DATA_ACTIVITY_IN = 0x00000001;
2814    /** Data connection activity: Currently sending IP PPP traffic. */
2815    public static final int DATA_ACTIVITY_OUT = 0x00000002;
2816    /** Data connection activity: Currently both sending and receiving
2817     *  IP PPP traffic. */
2818    public static final int DATA_ACTIVITY_INOUT = DATA_ACTIVITY_IN | DATA_ACTIVITY_OUT;
2819    /**
2820     * Data connection is active, but physical link is down
2821     */
2822    public static final int DATA_ACTIVITY_DORMANT = 0x00000004;
2823
2824    /**
2825     * Returns a constant indicating the type of activity on a data connection
2826     * (cellular).
2827     *
2828     * @see #DATA_ACTIVITY_NONE
2829     * @see #DATA_ACTIVITY_IN
2830     * @see #DATA_ACTIVITY_OUT
2831     * @see #DATA_ACTIVITY_INOUT
2832     * @see #DATA_ACTIVITY_DORMANT
2833     */
2834    public int getDataActivity() {
2835        try {
2836            ITelephony telephony = getITelephony();
2837            if (telephony == null)
2838                return DATA_ACTIVITY_NONE;
2839            return telephony.getDataActivity();
2840        } catch (RemoteException ex) {
2841            // the phone process is restarting.
2842            return DATA_ACTIVITY_NONE;
2843        } catch (NullPointerException ex) {
2844          // the phone process is restarting.
2845          return DATA_ACTIVITY_NONE;
2846      }
2847    }
2848
2849    /** Data connection state: Unknown.  Used before we know the state.
2850     * @hide
2851     */
2852    public static final int DATA_UNKNOWN        = -1;
2853    /** Data connection state: Disconnected. IP traffic not available. */
2854    public static final int DATA_DISCONNECTED   = 0;
2855    /** Data connection state: Currently setting up a data connection. */
2856    public static final int DATA_CONNECTING     = 1;
2857    /** Data connection state: Connected. IP traffic should be available. */
2858    public static final int DATA_CONNECTED      = 2;
2859    /** Data connection state: Suspended. The connection is up, but IP
2860     * traffic is temporarily unavailable. For example, in a 2G network,
2861     * data activity may be suspended when a voice call arrives. */
2862    public static final int DATA_SUSPENDED      = 3;
2863
2864    /**
2865     * Returns a constant indicating the current data connection state
2866     * (cellular).
2867     *
2868     * @see #DATA_DISCONNECTED
2869     * @see #DATA_CONNECTING
2870     * @see #DATA_CONNECTED
2871     * @see #DATA_SUSPENDED
2872     */
2873    public int getDataState() {
2874        try {
2875            ITelephony telephony = getITelephony();
2876            if (telephony == null)
2877                return DATA_DISCONNECTED;
2878            return telephony.getDataState();
2879        } catch (RemoteException ex) {
2880            // the phone process is restarting.
2881            return DATA_DISCONNECTED;
2882        } catch (NullPointerException ex) {
2883            return DATA_DISCONNECTED;
2884        }
2885    }
2886
2887   /**
2888    * @hide
2889    */
2890    private ITelephony getITelephony() {
2891        return ITelephony.Stub.asInterface(ServiceManager.getService(Context.TELEPHONY_SERVICE));
2892    }
2893
2894    /**
2895    * @hide
2896    */
2897    private ITelecomService getTelecomService() {
2898        return ITelecomService.Stub.asInterface(ServiceManager.getService(Context.TELECOM_SERVICE));
2899    }
2900
2901    //
2902    //
2903    // PhoneStateListener
2904    //
2905    //
2906
2907    /**
2908     * Registers a listener object to receive notification of changes
2909     * in specified telephony states.
2910     * <p>
2911     * To register a listener, pass a {@link PhoneStateListener}
2912     * and specify at least one telephony state of interest in
2913     * the events argument.
2914     *
2915     * At registration, and when a specified telephony state
2916     * changes, the telephony manager invokes the appropriate
2917     * callback method on the listener object and passes the
2918     * current (updated) values.
2919     * <p>
2920     * To unregister a listener, pass the listener object and set the
2921     * events argument to
2922     * {@link PhoneStateListener#LISTEN_NONE LISTEN_NONE} (0).
2923     *
2924     * @param listener The {@link PhoneStateListener} object to register
2925     *                 (or unregister)
2926     * @param events The telephony state(s) of interest to the listener,
2927     *               as a bitwise-OR combination of {@link PhoneStateListener}
2928     *               LISTEN_ flags.
2929     */
2930    public void listen(PhoneStateListener listener, int events) {
2931        if (mContext == null) return;
2932        try {
2933            Boolean notifyNow = (getITelephony() != null);
2934            sRegistry.listenForSubscriber(listener.mSubId, getOpPackageName(),
2935                    listener.callback, events, notifyNow);
2936        } catch (RemoteException ex) {
2937            // system process dead
2938        } catch (NullPointerException ex) {
2939            // system process dead
2940        }
2941    }
2942
2943    /**
2944     * Returns the CDMA ERI icon index to display
2945     *
2946     * <p>
2947     * Requires Permission:
2948     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2949     * @hide
2950     */
2951    public int getCdmaEriIconIndex() {
2952        return getCdmaEriIconIndex(getDefaultSubscription());
2953    }
2954
2955    /**
2956     * Returns the CDMA ERI icon index to display for a subscription
2957     * <p>
2958     * Requires Permission:
2959     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2960     */
2961    /** {@hide} */
2962    public int getCdmaEriIconIndex(int subId) {
2963        try {
2964            ITelephony telephony = getITelephony();
2965            if (telephony == null)
2966                return -1;
2967            return telephony.getCdmaEriIconIndexForSubscriber(subId, getOpPackageName());
2968        } catch (RemoteException ex) {
2969            // the phone process is restarting.
2970            return -1;
2971        } catch (NullPointerException ex) {
2972            return -1;
2973        }
2974    }
2975
2976    /**
2977     * Returns the CDMA ERI icon mode,
2978     * 0 - ON
2979     * 1 - FLASHING
2980     *
2981     * <p>
2982     * Requires Permission:
2983     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2984     * @hide
2985     */
2986    public int getCdmaEriIconMode() {
2987        return getCdmaEriIconMode(getDefaultSubscription());
2988    }
2989
2990    /**
2991     * Returns the CDMA ERI icon mode for a subscription.
2992     * 0 - ON
2993     * 1 - FLASHING
2994     *
2995     * <p>
2996     * Requires Permission:
2997     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
2998     */
2999    /** {@hide} */
3000    public int getCdmaEriIconMode(int subId) {
3001        try {
3002            ITelephony telephony = getITelephony();
3003            if (telephony == null)
3004                return -1;
3005            return telephony.getCdmaEriIconModeForSubscriber(subId, getOpPackageName());
3006        } catch (RemoteException ex) {
3007            // the phone process is restarting.
3008            return -1;
3009        } catch (NullPointerException ex) {
3010            return -1;
3011        }
3012    }
3013
3014    /**
3015     * Returns the CDMA ERI text,
3016     *
3017     * <p>
3018     * Requires Permission:
3019     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
3020     * @hide
3021     */
3022    public String getCdmaEriText() {
3023        return getCdmaEriText(getDefaultSubscription());
3024    }
3025
3026    /**
3027     * Returns the CDMA ERI text, of a subscription
3028     *
3029     * <p>
3030     * Requires Permission:
3031     *   {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE}
3032     */
3033    /** {@hide} */
3034    public String getCdmaEriText(int subId) {
3035        try {
3036            ITelephony telephony = getITelephony();
3037            if (telephony == null)
3038                return null;
3039            return telephony.getCdmaEriTextForSubscriber(subId, getOpPackageName());
3040        } catch (RemoteException ex) {
3041            // the phone process is restarting.
3042            return null;
3043        } catch (NullPointerException ex) {
3044            return null;
3045        }
3046    }
3047
3048    /**
3049     * @return true if the current device is "voice capable".
3050     * <p>
3051     * "Voice capable" means that this device supports circuit-switched
3052     * (i.e. voice) phone calls over the telephony network, and is allowed
3053     * to display the in-call UI while a cellular voice call is active.
3054     * This will be false on "data only" devices which can't make voice
3055     * calls and don't support any in-call UI.
3056     * <p>
3057     * Note: the meaning of this flag is subtly different from the
3058     * PackageManager.FEATURE_TELEPHONY system feature, which is available
3059     * on any device with a telephony radio, even if the device is
3060     * data-only.
3061     */
3062    public boolean isVoiceCapable() {
3063        if (mContext == null) return true;
3064        return mContext.getResources().getBoolean(
3065                com.android.internal.R.bool.config_voice_capable);
3066    }
3067
3068    /**
3069     * @return true if the current device supports sms service.
3070     * <p>
3071     * If true, this means that the device supports both sending and
3072     * receiving sms via the telephony network.
3073     * <p>
3074     * Note: Voicemail waiting sms, cell broadcasting sms, and MMS are
3075     *       disabled when device doesn't support sms.
3076     */
3077    public boolean isSmsCapable() {
3078        if (mContext == null) return true;
3079        return mContext.getResources().getBoolean(
3080                com.android.internal.R.bool.config_sms_capable);
3081    }
3082
3083    /**
3084     * Returns all observed cell information from all radios on the
3085     * device including the primary and neighboring cells. Calling this method does
3086     * not trigger a call to {@link android.telephony.PhoneStateListener#onCellInfoChanged
3087     * onCellInfoChanged()}, or change the rate at which
3088     * {@link android.telephony.PhoneStateListener#onCellInfoChanged
3089     * onCellInfoChanged()} is called.
3090     *
3091     *<p>
3092     * The list can include one or more {@link android.telephony.CellInfoGsm CellInfoGsm},
3093     * {@link android.telephony.CellInfoCdma CellInfoCdma},
3094     * {@link android.telephony.CellInfoLte CellInfoLte}, and
3095     * {@link android.telephony.CellInfoWcdma CellInfoWcdma} objects, in any combination.
3096     * On devices with multiple radios it is typical to see instances of
3097     * one or more of any these in the list. In addition, zero, one, or more
3098     * of the returned objects may be considered registered; that is, their
3099     * {@link android.telephony.CellInfo#isRegistered CellInfo.isRegistered()}
3100     * methods may return true.
3101     *
3102     * <p>This method returns valid data for registered cells on devices with
3103     * {@link android.content.pm.PackageManager#FEATURE_TELEPHONY}.
3104     *
3105     *<p>
3106     * This method is preferred over using {@link
3107     * android.telephony.TelephonyManager#getCellLocation getCellLocation()}.
3108     * However, for older devices, <code>getAllCellInfo()</code> may return
3109     * null. In these cases, you should call {@link
3110     * android.telephony.TelephonyManager#getCellLocation getCellLocation()}
3111     * instead.
3112     *
3113     * <p>Requires permission:
3114     * {@link android.Manifest.permission#ACCESS_COARSE_LOCATION}
3115     *
3116     * @return List of {@link android.telephony.CellInfo}; null if cell
3117     * information is unavailable.
3118     *
3119     */
3120    public List<CellInfo> getAllCellInfo() {
3121        try {
3122            ITelephony telephony = getITelephony();
3123            if (telephony == null)
3124                return null;
3125            return telephony.getAllCellInfo(getOpPackageName());
3126        } catch (RemoteException ex) {
3127            return null;
3128        } catch (NullPointerException ex) {
3129            return null;
3130        }
3131    }
3132
3133    /**
3134     * Sets the minimum time in milli-seconds between {@link PhoneStateListener#onCellInfoChanged
3135     * PhoneStateListener.onCellInfoChanged} will be invoked.
3136     *<p>
3137     * The default, 0, means invoke onCellInfoChanged when any of the reported
3138     * information changes. Setting the value to INT_MAX(0x7fffffff) means never issue
3139     * A onCellInfoChanged.
3140     *<p>
3141     * @param rateInMillis the rate
3142     *
3143     * @hide
3144     */
3145    public void setCellInfoListRate(int rateInMillis) {
3146        try {
3147            ITelephony telephony = getITelephony();
3148            if (telephony != null)
3149                telephony.setCellInfoListRate(rateInMillis);
3150        } catch (RemoteException ex) {
3151        } catch (NullPointerException ex) {
3152        }
3153    }
3154
3155    /**
3156     * Returns the MMS user agent.
3157     */
3158    public String getMmsUserAgent() {
3159        if (mContext == null) return null;
3160        return mContext.getResources().getString(
3161                com.android.internal.R.string.config_mms_user_agent);
3162    }
3163
3164    /**
3165     * Returns the MMS user agent profile URL.
3166     */
3167    public String getMmsUAProfUrl() {
3168        if (mContext == null) return null;
3169        return mContext.getResources().getString(
3170                com.android.internal.R.string.config_mms_user_agent_profile_url);
3171    }
3172
3173    /**
3174     * Opens a logical channel to the ICC card.
3175     *
3176     * Input parameters equivalent to TS 27.007 AT+CCHO command.
3177     *
3178     * <p>Requires Permission:
3179     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3180     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3181     *
3182     * @param AID Application id. See ETSI 102.221 and 101.220.
3183     * @return an IccOpenLogicalChannelResponse object.
3184     */
3185    public IccOpenLogicalChannelResponse iccOpenLogicalChannel(String AID) {
3186        return iccOpenLogicalChannel(getDefaultSubscription(), AID);
3187    }
3188
3189    /**
3190     * Opens a logical channel to the ICC card.
3191     *
3192     * Input parameters equivalent to TS 27.007 AT+CCHO command.
3193     *
3194     * <p>Requires Permission:
3195     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3196     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3197     *
3198     * @param subId The subscription to use.
3199     * @param AID Application id. See ETSI 102.221 and 101.220.
3200     * @return an IccOpenLogicalChannelResponse object.
3201     */
3202    public IccOpenLogicalChannelResponse iccOpenLogicalChannel(int subId, String AID) {
3203        try {
3204            ITelephony telephony = getITelephony();
3205            if (telephony != null)
3206                return telephony.iccOpenLogicalChannel(subId, AID);
3207        } catch (RemoteException ex) {
3208        } catch (NullPointerException ex) {
3209        }
3210        return null;
3211    }
3212
3213    /**
3214     * Closes a previously opened logical channel to the ICC card.
3215     *
3216     * Input parameters equivalent to TS 27.007 AT+CCHC command.
3217     *
3218     * <p>Requires Permission:
3219     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3220     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3221     *
3222     * @param channel is the channel id to be closed as retruned by a successful
3223     *            iccOpenLogicalChannel.
3224     * @return true if the channel was closed successfully.
3225     */
3226    public boolean iccCloseLogicalChannel(int channel) {
3227        return iccCloseLogicalChannel(getDefaultSubscription(), channel);
3228    }
3229
3230    /**
3231     * Closes a previously opened logical channel to the ICC card.
3232     *
3233     * Input parameters equivalent to TS 27.007 AT+CCHC command.
3234     *
3235     * <p>Requires Permission:
3236     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3237     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3238     *
3239     * @param subId The subscription to use.
3240     * @param channel is the channel id to be closed as retruned by a successful
3241     *            iccOpenLogicalChannel.
3242     * @return true if the channel was closed successfully.
3243     */
3244    public boolean iccCloseLogicalChannel(int subId, int channel) {
3245        try {
3246            ITelephony telephony = getITelephony();
3247            if (telephony != null)
3248                return telephony.iccCloseLogicalChannel(subId, channel);
3249        } catch (RemoteException ex) {
3250        } catch (NullPointerException ex) {
3251        }
3252        return false;
3253    }
3254
3255    /**
3256     * Transmit an APDU to the ICC card over a logical channel.
3257     *
3258     * Input parameters equivalent to TS 27.007 AT+CGLA command.
3259     *
3260     * <p>Requires Permission:
3261     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3262     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3263     *
3264     * @param channel is the channel id to be closed as returned by a successful
3265     *            iccOpenLogicalChannel.
3266     * @param cla Class of the APDU command.
3267     * @param instruction Instruction of the APDU command.
3268     * @param p1 P1 value of the APDU command.
3269     * @param p2 P2 value of the APDU command.
3270     * @param p3 P3 value of the APDU command. If p3 is negative a 4 byte APDU
3271     *            is sent to the SIM.
3272     * @param data Data to be sent with the APDU.
3273     * @return The APDU response from the ICC card with the status appended at
3274     *            the end.
3275     */
3276    public String iccTransmitApduLogicalChannel(int channel, int cla,
3277            int instruction, int p1, int p2, int p3, String data) {
3278        return iccTransmitApduLogicalChannel(getDefaultSubscription(), channel, cla,
3279                    instruction, p1, p2, p3, data);
3280    }
3281
3282    /**
3283     * Transmit an APDU to the ICC card over a logical channel.
3284     *
3285     * Input parameters equivalent to TS 27.007 AT+CGLA command.
3286     *
3287     * <p>Requires Permission:
3288     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3289     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3290     *
3291     * @param subId The subscription to use.
3292     * @param channel is the channel id to be closed as returned by a successful
3293     *            iccOpenLogicalChannel.
3294     * @param cla Class of the APDU command.
3295     * @param instruction Instruction of the APDU command.
3296     * @param p1 P1 value of the APDU command.
3297     * @param p2 P2 value of the APDU command.
3298     * @param p3 P3 value of the APDU command. If p3 is negative a 4 byte APDU
3299     *            is sent to the SIM.
3300     * @param data Data to be sent with the APDU.
3301     * @return The APDU response from the ICC card with the status appended at
3302     *            the end.
3303     */
3304    public String iccTransmitApduLogicalChannel(int subId, int channel, int cla,
3305            int instruction, int p1, int p2, int p3, String data) {
3306        try {
3307            ITelephony telephony = getITelephony();
3308            if (telephony != null)
3309                return telephony.iccTransmitApduLogicalChannel(subId, channel, cla,
3310                    instruction, p1, p2, p3, data);
3311        } catch (RemoteException ex) {
3312        } catch (NullPointerException ex) {
3313        }
3314        return "";
3315    }
3316
3317    /**
3318     * Transmit an APDU to the ICC card over the basic channel.
3319     *
3320     * Input parameters equivalent to TS 27.007 AT+CSIM command.
3321     *
3322     * <p>Requires Permission:
3323     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3324     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3325     *
3326     * @param cla Class of the APDU command.
3327     * @param instruction Instruction of the APDU command.
3328     * @param p1 P1 value of the APDU command.
3329     * @param p2 P2 value of the APDU command.
3330     * @param p3 P3 value of the APDU command. If p3 is negative a 4 byte APDU
3331     *            is sent to the SIM.
3332     * @param data Data to be sent with the APDU.
3333     * @return The APDU response from the ICC card with the status appended at
3334     *            the end.
3335     */
3336    public String iccTransmitApduBasicChannel(int cla,
3337            int instruction, int p1, int p2, int p3, String data) {
3338        return iccTransmitApduBasicChannel(getDefaultSubscription(), cla,
3339                    instruction, p1, p2, p3, data);
3340    }
3341
3342    /**
3343     * Transmit an APDU to the ICC card over the basic channel.
3344     *
3345     * Input parameters equivalent to TS 27.007 AT+CSIM command.
3346     *
3347     * <p>Requires Permission:
3348     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3349     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3350     *
3351     * @param subId The subscription to use.
3352     * @param cla Class of the APDU command.
3353     * @param instruction Instruction of the APDU command.
3354     * @param p1 P1 value of the APDU command.
3355     * @param p2 P2 value of the APDU command.
3356     * @param p3 P3 value of the APDU command. If p3 is negative a 4 byte APDU
3357     *            is sent to the SIM.
3358     * @param data Data to be sent with the APDU.
3359     * @return The APDU response from the ICC card with the status appended at
3360     *            the end.
3361     */
3362    public String iccTransmitApduBasicChannel(int subId, int cla,
3363            int instruction, int p1, int p2, int p3, String data) {
3364        try {
3365            ITelephony telephony = getITelephony();
3366            if (telephony != null)
3367                return telephony.iccTransmitApduBasicChannel(subId, cla,
3368                    instruction, p1, p2, p3, data);
3369        } catch (RemoteException ex) {
3370        } catch (NullPointerException ex) {
3371        }
3372        return "";
3373    }
3374
3375    /**
3376     * Returns the response APDU for a command APDU sent through SIM_IO.
3377     *
3378     * <p>Requires Permission:
3379     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3380     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3381     *
3382     * @param fileID
3383     * @param command
3384     * @param p1 P1 value of the APDU command.
3385     * @param p2 P2 value of the APDU command.
3386     * @param p3 P3 value of the APDU command.
3387     * @param filePath
3388     * @return The APDU response.
3389     */
3390    public byte[] iccExchangeSimIO(int fileID, int command, int p1, int p2, int p3,
3391            String filePath) {
3392        return iccExchangeSimIO(getDefaultSubscription(), fileID, command, p1, p2, p3, filePath);
3393    }
3394
3395    /**
3396     * Returns the response APDU for a command APDU sent through SIM_IO.
3397     *
3398     * <p>Requires Permission:
3399     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3400     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3401     *
3402     * @param subId The subscription to use.
3403     * @param fileID
3404     * @param command
3405     * @param p1 P1 value of the APDU command.
3406     * @param p2 P2 value of the APDU command.
3407     * @param p3 P3 value of the APDU command.
3408     * @param filePath
3409     * @return The APDU response.
3410     */
3411    public byte[] iccExchangeSimIO(int subId, int fileID, int command, int p1, int p2,
3412            int p3, String filePath) {
3413        try {
3414            ITelephony telephony = getITelephony();
3415            if (telephony != null)
3416                return telephony.iccExchangeSimIO(subId, fileID, command, p1, p2, p3, filePath);
3417        } catch (RemoteException ex) {
3418        } catch (NullPointerException ex) {
3419        }
3420        return null;
3421    }
3422
3423    /**
3424     * Send ENVELOPE to the SIM and return the response.
3425     *
3426     * <p>Requires Permission:
3427     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3428     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3429     *
3430     * @param content String containing SAT/USAT response in hexadecimal
3431     *                format starting with command tag. See TS 102 223 for
3432     *                details.
3433     * @return The APDU response from the ICC card in hexadecimal format
3434     *         with the last 4 bytes being the status word. If the command fails,
3435     *         returns an empty string.
3436     */
3437    public String sendEnvelopeWithStatus(String content) {
3438        return sendEnvelopeWithStatus(getDefaultSubscription(), content);
3439    }
3440
3441    /**
3442     * Send ENVELOPE to the SIM and return the response.
3443     *
3444     * <p>Requires Permission:
3445     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3446     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3447     *
3448     * @param subId The subscription to use.
3449     * @param content String containing SAT/USAT response in hexadecimal
3450     *                format starting with command tag. See TS 102 223 for
3451     *                details.
3452     * @return The APDU response from the ICC card in hexadecimal format
3453     *         with the last 4 bytes being the status word. If the command fails,
3454     *         returns an empty string.
3455     */
3456    public String sendEnvelopeWithStatus(int subId, String content) {
3457        try {
3458            ITelephony telephony = getITelephony();
3459            if (telephony != null)
3460                return telephony.sendEnvelopeWithStatus(subId, content);
3461        } catch (RemoteException ex) {
3462        } catch (NullPointerException ex) {
3463        }
3464        return "";
3465    }
3466
3467    /**
3468     * Read one of the NV items defined in com.android.internal.telephony.RadioNVItems.
3469     * Used for device configuration by some CDMA operators.
3470     * <p>
3471     * Requires Permission:
3472     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3473     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3474     *
3475     * @param itemID the ID of the item to read.
3476     * @return the NV item as a String, or null on any failure.
3477     *
3478     * @hide
3479     */
3480    public String nvReadItem(int itemID) {
3481        try {
3482            ITelephony telephony = getITelephony();
3483            if (telephony != null)
3484                return telephony.nvReadItem(itemID);
3485        } catch (RemoteException ex) {
3486            Rlog.e(TAG, "nvReadItem RemoteException", ex);
3487        } catch (NullPointerException ex) {
3488            Rlog.e(TAG, "nvReadItem NPE", ex);
3489        }
3490        return "";
3491    }
3492
3493    /**
3494     * Write one of the NV items defined in com.android.internal.telephony.RadioNVItems.
3495     * Used for device configuration by some CDMA operators.
3496     * <p>
3497     * Requires Permission:
3498     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3499     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3500     *
3501     * @param itemID the ID of the item to read.
3502     * @param itemValue the value to write, as a String.
3503     * @return true on success; false on any failure.
3504     *
3505     * @hide
3506     */
3507    public boolean nvWriteItem(int itemID, String itemValue) {
3508        try {
3509            ITelephony telephony = getITelephony();
3510            if (telephony != null)
3511                return telephony.nvWriteItem(itemID, itemValue);
3512        } catch (RemoteException ex) {
3513            Rlog.e(TAG, "nvWriteItem RemoteException", ex);
3514        } catch (NullPointerException ex) {
3515            Rlog.e(TAG, "nvWriteItem NPE", ex);
3516        }
3517        return false;
3518    }
3519
3520    /**
3521     * Update the CDMA Preferred Roaming List (PRL) in the radio NV storage.
3522     * Used for device configuration by some CDMA operators.
3523     * <p>
3524     * Requires Permission:
3525     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3526     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3527     *
3528     * @param preferredRoamingList byte array containing the new PRL.
3529     * @return true on success; false on any failure.
3530     *
3531     * @hide
3532     */
3533    public boolean nvWriteCdmaPrl(byte[] preferredRoamingList) {
3534        try {
3535            ITelephony telephony = getITelephony();
3536            if (telephony != null)
3537                return telephony.nvWriteCdmaPrl(preferredRoamingList);
3538        } catch (RemoteException ex) {
3539            Rlog.e(TAG, "nvWriteCdmaPrl RemoteException", ex);
3540        } catch (NullPointerException ex) {
3541            Rlog.e(TAG, "nvWriteCdmaPrl NPE", ex);
3542        }
3543        return false;
3544    }
3545
3546    /**
3547     * Perform the specified type of NV config reset. The radio will be taken offline
3548     * and the device must be rebooted after the operation. Used for device
3549     * configuration by some CDMA operators.
3550     * <p>
3551     * Requires Permission:
3552     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3553     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3554     *
3555     * @param resetType reset type: 1: reload NV reset, 2: erase NV reset, 3: factory NV reset
3556     * @return true on success; false on any failure.
3557     *
3558     * @hide
3559     */
3560    public boolean nvResetConfig(int resetType) {
3561        try {
3562            ITelephony telephony = getITelephony();
3563            if (telephony != null)
3564                return telephony.nvResetConfig(resetType);
3565        } catch (RemoteException ex) {
3566            Rlog.e(TAG, "nvResetConfig RemoteException", ex);
3567        } catch (NullPointerException ex) {
3568            Rlog.e(TAG, "nvResetConfig NPE", ex);
3569        }
3570        return false;
3571    }
3572
3573    /**
3574     * Returns Default subscription.
3575     */
3576    private static int getDefaultSubscription() {
3577        return SubscriptionManager.getDefaultSubscriptionId();
3578    }
3579
3580    /**
3581     * Returns Default phone.
3582     */
3583    private static int getDefaultPhone() {
3584        return SubscriptionManager.getPhoneId(SubscriptionManager.getDefaultSubscriptionId());
3585    }
3586
3587    /** {@hide} */
3588    public int getDefaultSim() {
3589        return SubscriptionManager.getSlotId(SubscriptionManager.getDefaultSubscriptionId());
3590    }
3591
3592    /**
3593     * Sets the telephony property with the value specified.
3594     *
3595     * @hide
3596     */
3597    public static void setTelephonyProperty(int phoneId, String property, String value) {
3598        String propVal = "";
3599        String p[] = null;
3600        String prop = SystemProperties.get(property);
3601
3602        if (value == null) {
3603            value = "";
3604        }
3605
3606        if (prop != null) {
3607            p = prop.split(",");
3608        }
3609
3610        if (!SubscriptionManager.isValidPhoneId(phoneId)) {
3611            Rlog.d(TAG, "setTelephonyProperty: invalid phoneId=" + phoneId +
3612                    " property=" + property + " value: " + value + " prop=" + prop);
3613            return;
3614        }
3615
3616        for (int i = 0; i < phoneId; i++) {
3617            String str = "";
3618            if ((p != null) && (i < p.length)) {
3619                str = p[i];
3620            }
3621            propVal = propVal + str + ",";
3622        }
3623
3624        propVal = propVal + value;
3625        if (p != null) {
3626            for (int i = phoneId + 1; i < p.length; i++) {
3627                propVal = propVal + "," + p[i];
3628            }
3629        }
3630
3631        if (property.length() > SystemProperties.PROP_NAME_MAX
3632                || propVal.length() > SystemProperties.PROP_VALUE_MAX) {
3633            Rlog.d(TAG, "setTelephonyProperty: property to long phoneId=" + phoneId +
3634                    " property=" + property + " value: " + value + " propVal=" + propVal);
3635            return;
3636        }
3637
3638        Rlog.d(TAG, "setTelephonyProperty: success phoneId=" + phoneId +
3639                " property=" + property + " value: " + value + " propVal=" + propVal);
3640        SystemProperties.set(property, propVal);
3641    }
3642
3643    /**
3644     * Convenience function for retrieving a value from the secure settings
3645     * value list as an integer.  Note that internally setting values are
3646     * always stored as strings; this function converts the string to an
3647     * integer for you.
3648     * <p>
3649     * This version does not take a default value.  If the setting has not
3650     * been set, or the string value is not a number,
3651     * it throws {@link SettingNotFoundException}.
3652     *
3653     * @param cr The ContentResolver to access.
3654     * @param name The name of the setting to retrieve.
3655     * @param index The index of the list
3656     *
3657     * @throws SettingNotFoundException Thrown if a setting by the given
3658     * name can't be found or the setting value is not an integer.
3659     *
3660     * @return The value at the given index of settings.
3661     * @hide
3662     */
3663    public static int getIntAtIndex(android.content.ContentResolver cr,
3664            String name, int index)
3665            throws android.provider.Settings.SettingNotFoundException {
3666        String v = android.provider.Settings.Global.getString(cr, name);
3667        if (v != null) {
3668            String valArray[] = v.split(",");
3669            if ((index >= 0) && (index < valArray.length) && (valArray[index] != null)) {
3670                try {
3671                    return Integer.parseInt(valArray[index]);
3672                } catch (NumberFormatException e) {
3673                    //Log.e(TAG, "Exception while parsing Integer: ", e);
3674                }
3675            }
3676        }
3677        throw new android.provider.Settings.SettingNotFoundException(name);
3678    }
3679
3680    /**
3681     * Convenience function for updating settings value as coma separated
3682     * integer values. This will either create a new entry in the table if the
3683     * given name does not exist, or modify the value of the existing row
3684     * with that name.  Note that internally setting values are always
3685     * stored as strings, so this function converts the given value to a
3686     * string before storing it.
3687     *
3688     * @param cr The ContentResolver to access.
3689     * @param name The name of the setting to modify.
3690     * @param index The index of the list
3691     * @param value The new value for the setting to be added to the list.
3692     * @return true if the value was set, false on database errors
3693     * @hide
3694     */
3695    public static boolean putIntAtIndex(android.content.ContentResolver cr,
3696            String name, int index, int value) {
3697        String data = "";
3698        String valArray[] = null;
3699        String v = android.provider.Settings.Global.getString(cr, name);
3700
3701        if (index == Integer.MAX_VALUE) {
3702            throw new RuntimeException("putIntAtIndex index == MAX_VALUE index=" + index);
3703        }
3704        if (index < 0) {
3705            throw new RuntimeException("putIntAtIndex index < 0 index=" + index);
3706        }
3707        if (v != null) {
3708            valArray = v.split(",");
3709        }
3710
3711        // Copy the elements from valArray till index
3712        for (int i = 0; i < index; i++) {
3713            String str = "";
3714            if ((valArray != null) && (i < valArray.length)) {
3715                str = valArray[i];
3716            }
3717            data = data + str + ",";
3718        }
3719
3720        data = data + value;
3721
3722        // Copy the remaining elements from valArray if any.
3723        if (valArray != null) {
3724            for (int i = index+1; i < valArray.length; i++) {
3725                data = data + "," + valArray[i];
3726            }
3727        }
3728        return android.provider.Settings.Global.putString(cr, name, data);
3729    }
3730
3731    /**
3732     * Gets the telephony property.
3733     *
3734     * @hide
3735     */
3736    public static String getTelephonyProperty(int phoneId, String property, String defaultVal) {
3737        String propVal = null;
3738        String prop = SystemProperties.get(property);
3739        if ((prop != null) && (prop.length() > 0)) {
3740            String values[] = prop.split(",");
3741            if ((phoneId >= 0) && (phoneId < values.length) && (values[phoneId] != null)) {
3742                propVal = values[phoneId];
3743            }
3744        }
3745        return propVal == null ? defaultVal : propVal;
3746    }
3747
3748    /** @hide */
3749    public int getSimCount() {
3750        // FIXME Need to get it from Telephony Dev Controller when that gets implemented!
3751        // and then this method shouldn't be used at all!
3752        if(isMultiSimEnabled()) {
3753            return 2;
3754        } else {
3755            return 1;
3756        }
3757    }
3758
3759    /**
3760     * Returns the IMS Service Table (IST) that was loaded from the ISIM.
3761     * @return IMS Service Table or null if not present or not loaded
3762     * @hide
3763     */
3764    public String getIsimIst() {
3765        try {
3766            IPhoneSubInfo info = getSubscriberInfo();
3767            if (info == null)
3768                return null;
3769            return info.getIsimIst();
3770        } catch (RemoteException ex) {
3771            return null;
3772        } catch (NullPointerException ex) {
3773            // This could happen before phone restarts due to crashing
3774            return null;
3775        }
3776    }
3777
3778    /**
3779     * Returns the IMS Proxy Call Session Control Function(PCSCF) that were loaded from the ISIM.
3780     * @return an array of PCSCF strings with one PCSCF per string, or null if
3781     *         not present or not loaded
3782     * @hide
3783     */
3784    public String[] getIsimPcscf() {
3785        try {
3786            IPhoneSubInfo info = getSubscriberInfo();
3787            if (info == null)
3788                return null;
3789            return info.getIsimPcscf();
3790        } catch (RemoteException ex) {
3791            return null;
3792        } catch (NullPointerException ex) {
3793            // This could happen before phone restarts due to crashing
3794            return null;
3795        }
3796    }
3797
3798    /**
3799     * Returns the response of ISIM Authetification through RIL.
3800     * Returns null if the Authentification hasn't been successed or isn't present iphonesubinfo.
3801     * @return the response of ISIM Authetification, or null if not available
3802     * @hide
3803     * @deprecated
3804     * @see getIccAuthentication with appType=PhoneConstants.APPTYPE_ISIM
3805     */
3806    public String getIsimChallengeResponse(String nonce){
3807        try {
3808            IPhoneSubInfo info = getSubscriberInfo();
3809            if (info == null)
3810                return null;
3811            return info.getIsimChallengeResponse(nonce);
3812        } catch (RemoteException ex) {
3813            return null;
3814        } catch (NullPointerException ex) {
3815            // This could happen before phone restarts due to crashing
3816            return null;
3817        }
3818    }
3819
3820    // ICC SIM Application Types
3821    /** UICC application type is SIM */
3822    public static final int APPTYPE_SIM = PhoneConstants.APPTYPE_SIM;
3823    /** UICC application type is USIM */
3824    public static final int APPTYPE_USIM = PhoneConstants.APPTYPE_USIM;
3825    /** UICC application type is RUIM */
3826    public static final int APPTYPE_RUIM = PhoneConstants.APPTYPE_RUIM;
3827    /** UICC application type is CSIM */
3828    public static final int APPTYPE_CSIM = PhoneConstants.APPTYPE_CSIM;
3829    /** UICC application type is ISIM */
3830    public static final int APPTYPE_ISIM = PhoneConstants.APPTYPE_ISIM;
3831    // authContext (parameter P2) when doing UICC challenge,
3832    // per 3GPP TS 31.102 (Section 7.1.2)
3833    /** Authentication type for UICC challenge is EAP SIM. See RFC 4186 for details. */
3834    public static final int AUTHTYPE_EAP_SIM = PhoneConstants.AUTH_CONTEXT_EAP_SIM;
3835    /** Authentication type for UICC challenge is EAP AKA. See RFC 4187 for details. */
3836    public static final int AUTHTYPE_EAP_AKA = PhoneConstants.AUTH_CONTEXT_EAP_AKA;
3837
3838    /**
3839     * Returns the response of authentication for the default subscription.
3840     * Returns null if the authentication hasn't been successful
3841     *
3842     * <p>Requires that the calling app has carrier privileges or READ_PRIVILEGED_PHONE_STATE
3843     * permission.
3844     *
3845     * @param appType the icc application type, like {@link #APPTYPE_USIM}
3846     * @param authType the authentication type, {@link #AUTHTYPE_EAP_AKA} or
3847     * {@link #AUTHTYPE_EAP_SIM}
3848     * @param data authentication challenge data, base64 encoded.
3849     * See 3GPP TS 31.102 7.1.2 for more details.
3850     * @return the response of authentication, or null if not available
3851     *
3852     * @see #hasCarrierPrivileges
3853     */
3854    public String getIccAuthentication(int appType, int authType, String data) {
3855        return getIccAuthentication(getDefaultSubscription(), appType, authType, data);
3856    }
3857
3858    /**
3859     * Returns the response of USIM Authentication for specified subId.
3860     * Returns null if the authentication hasn't been successful
3861     *
3862     * <p>Requires that the calling app has carrier privileges.
3863     *
3864     * @param subId subscription ID used for authentication
3865     * @param appType the icc application type, like {@link #APPTYPE_USIM}
3866     * @param authType the authentication type, {@link #AUTHTYPE_EAP_AKA} or
3867     * {@link #AUTHTYPE_EAP_SIM}
3868     * @param data authentication challenge data, base64 encoded.
3869     * See 3GPP TS 31.102 7.1.2 for more details.
3870     * @return the response of authentication, or null if not available
3871     *
3872     * @see #hasCarrierPrivileges
3873     */
3874
3875    public String getIccAuthentication(int subId, int appType, int authType, String data) {
3876        try {
3877            IPhoneSubInfo info = getSubscriberInfo();
3878            if (info == null)
3879                return null;
3880            return info.getIccSimChallengeResponse(subId, appType, authType, data);
3881        } catch (RemoteException ex) {
3882            return null;
3883        } catch (NullPointerException ex) {
3884            // This could happen before phone starts
3885            return null;
3886        }
3887    }
3888
3889    /**
3890     * Get P-CSCF address from PCO after data connection is established or modified.
3891     * @param apnType the apnType, "ims" for IMS APN, "emergency" for EMERGENCY APN
3892     * @return array of P-CSCF address
3893     * @hide
3894     */
3895    public String[] getPcscfAddress(String apnType) {
3896        try {
3897            ITelephony telephony = getITelephony();
3898            if (telephony == null)
3899                return new String[0];
3900            return telephony.getPcscfAddress(apnType, getOpPackageName());
3901        } catch (RemoteException e) {
3902            return new String[0];
3903        }
3904    }
3905
3906    /**
3907     * Set IMS registration state
3908     *
3909     * @param Registration state
3910     * @hide
3911     */
3912    public void setImsRegistrationState(boolean registered) {
3913        try {
3914            ITelephony telephony = getITelephony();
3915            if (telephony != null)
3916                telephony.setImsRegistrationState(registered);
3917        } catch (RemoteException e) {
3918        }
3919    }
3920
3921    /**
3922     * Get the preferred network type.
3923     * Used for device configuration by some CDMA operators.
3924     * <p>
3925     * Requires Permission:
3926     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3927     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3928     *
3929     * @return the preferred network type, defined in RILConstants.java.
3930     * @hide
3931     */
3932    public int getPreferredNetworkType(int subId) {
3933        try {
3934            ITelephony telephony = getITelephony();
3935            if (telephony != null)
3936                return telephony.getPreferredNetworkType(subId);
3937        } catch (RemoteException ex) {
3938            Rlog.e(TAG, "getPreferredNetworkType RemoteException", ex);
3939        } catch (NullPointerException ex) {
3940            Rlog.e(TAG, "getPreferredNetworkType NPE", ex);
3941        }
3942        return -1;
3943    }
3944
3945    /**
3946     * Sets the network selection mode to automatic.
3947     * <p>
3948     * Requires Permission:
3949     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3950     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3951     *
3952     * @hide
3953     */
3954    public void setNetworkSelectionModeAutomatic(int subId) {
3955        try {
3956            ITelephony telephony = getITelephony();
3957            if (telephony != null)
3958                telephony.setNetworkSelectionModeAutomatic(subId);
3959        } catch (RemoteException ex) {
3960            Rlog.e(TAG, "setNetworkSelectionModeAutomatic RemoteException", ex);
3961        } catch (NullPointerException ex) {
3962            Rlog.e(TAG, "setNetworkSelectionModeAutomatic NPE", ex);
3963        }
3964    }
3965
3966    /**
3967     * Perform a radio scan and return the list of avialble networks.
3968     *
3969     * The return value is a list of the OperatorInfo of the networks found. Note that this
3970     * scan can take a long time (sometimes minutes) to happen.
3971     *
3972     * <p>
3973     * Requires Permission:
3974     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3975     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3976     *
3977     * @hide
3978     */
3979    public CellNetworkScanResult getCellNetworkScanResults(int subId) {
3980        try {
3981            ITelephony telephony = getITelephony();
3982            if (telephony != null)
3983                return telephony.getCellNetworkScanResults(subId);
3984        } catch (RemoteException ex) {
3985            Rlog.e(TAG, "getCellNetworkScanResults RemoteException", ex);
3986        } catch (NullPointerException ex) {
3987            Rlog.e(TAG, "getCellNetworkScanResults NPE", ex);
3988        }
3989        return null;
3990    }
3991
3992    /**
3993     * Ask the radio to connect to the input network and change selection mode to manual.
3994     *
3995     * <p>
3996     * Requires Permission:
3997     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
3998     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
3999     *
4000     * @hide
4001     */
4002    public boolean setNetworkSelectionModeManual(int subId, OperatorInfo operator,
4003            boolean persistSelection) {
4004        try {
4005            ITelephony telephony = getITelephony();
4006            if (telephony != null)
4007                return telephony.setNetworkSelectionModeManual(subId, operator, persistSelection);
4008        } catch (RemoteException ex) {
4009            Rlog.e(TAG, "setNetworkSelectionModeManual RemoteException", ex);
4010        } catch (NullPointerException ex) {
4011            Rlog.e(TAG, "setNetworkSelectionModeManual NPE", ex);
4012        }
4013        return false;
4014    }
4015
4016    /**
4017     * Set the preferred network type.
4018     * Used for device configuration by some CDMA operators.
4019     * <p>
4020     * Requires Permission:
4021     *   {@link android.Manifest.permission#MODIFY_PHONE_STATE MODIFY_PHONE_STATE}
4022     * Or the calling app has carrier privileges. @see #hasCarrierPrivileges
4023     *
4024     * @param subId the id of the subscription to set the preferred network type for.
4025     * @param networkType the preferred network type, defined in RILConstants.java.
4026     * @return true on success; false on any failure.
4027     * @hide
4028     */
4029    public boolean setPreferredNetworkType(int subId, int networkType) {
4030        try {
4031            ITelephony telephony = getITelephony();
4032            if (telephony != null)
4033                return telephony.setPreferredNetworkType(subId, networkType);
4034        } catch (RemoteException ex) {
4035            Rlog.e(TAG, "setPreferredNetworkType RemoteException", ex);
4036        } catch (NullPointerException ex) {
4037            Rlog.e(TAG, "setPreferredNetworkType NPE", ex);
4038        }
4039        return false;
4040    }
4041
4042    /**
4043     * Set the preferred network type to global mode which includes LTE, CDMA, EvDo and GSM/WCDMA.
4044     *
4045     * <p>
4046     * Requires that the calling app has carrier privileges.
4047     * @see #hasCarrierPrivileges
4048     *
4049     * @return true on success; false on any failure.
4050     */
4051    public boolean setPreferredNetworkTypeToGlobal() {
4052        return setPreferredNetworkTypeToGlobal(getDefaultSubscription());
4053    }
4054
4055    /**
4056     * Set the preferred network type to global mode which includes LTE, CDMA, EvDo and GSM/WCDMA.
4057     *
4058     * <p>
4059     * Requires that the calling app has carrier privileges.
4060     * @see #hasCarrierPrivileges
4061     *
4062     * @return true on success; false on any failure.
4063     */
4064    public boolean setPreferredNetworkTypeToGlobal(int subId) {
4065        return setPreferredNetworkType(subId, RILConstants.NETWORK_MODE_LTE_CDMA_EVDO_GSM_WCDMA);
4066    }
4067
4068    /**
4069     * Check TETHER_DUN_REQUIRED and TETHER_DUN_APN settings, net.tethering.noprovisioning
4070     * SystemProperty, and config_tether_apndata to decide whether DUN APN is required for
4071     * tethering.
4072     *
4073     * @return 0: Not required. 1: required. 2: Not set.
4074     * @hide
4075     */
4076    public int getTetherApnRequired() {
4077        try {
4078            ITelephony telephony = getITelephony();
4079            if (telephony != null)
4080                return telephony.getTetherApnRequired();
4081        } catch (RemoteException ex) {
4082            Rlog.e(TAG, "hasMatchedTetherApnSetting RemoteException", ex);
4083        } catch (NullPointerException ex) {
4084            Rlog.e(TAG, "hasMatchedTetherApnSetting NPE", ex);
4085        }
4086        return 2;
4087    }
4088
4089
4090    /**
4091     * Values used to return status for hasCarrierPrivileges call.
4092     */
4093    /** @hide */ @SystemApi
4094    public static final int CARRIER_PRIVILEGE_STATUS_HAS_ACCESS = 1;
4095    /** @hide */ @SystemApi
4096    public static final int CARRIER_PRIVILEGE_STATUS_NO_ACCESS = 0;
4097    /** @hide */ @SystemApi
4098    public static final int CARRIER_PRIVILEGE_STATUS_RULES_NOT_LOADED = -1;
4099    /** @hide */ @SystemApi
4100    public static final int CARRIER_PRIVILEGE_STATUS_ERROR_LOADING_RULES = -2;
4101
4102    /**
4103     * Has the calling application been granted carrier privileges by the carrier.
4104     *
4105     * If any of the packages in the calling UID has carrier privileges, the
4106     * call will return true. This access is granted by the owner of the UICC
4107     * card and does not depend on the registered carrier.
4108     *
4109     * @return true if the app has carrier privileges.
4110     */
4111    public boolean hasCarrierPrivileges() {
4112        return hasCarrierPrivileges(getDefaultSubscription());
4113    }
4114
4115    /**
4116     * Has the calling application been granted carrier privileges by the carrier.
4117     *
4118     * If any of the packages in the calling UID has carrier privileges, the
4119     * call will return true. This access is granted by the owner of the UICC
4120     * card and does not depend on the registered carrier.
4121     *
4122     * @param subId The subscription to use.
4123     * @return true if the app has carrier privileges.
4124     */
4125    public boolean hasCarrierPrivileges(int subId) {
4126        try {
4127            ITelephony telephony = getITelephony();
4128            if (telephony != null) {
4129                return telephony.getCarrierPrivilegeStatus(subId) ==
4130                    CARRIER_PRIVILEGE_STATUS_HAS_ACCESS;
4131            }
4132        } catch (RemoteException ex) {
4133            Rlog.e(TAG, "hasCarrierPrivileges RemoteException", ex);
4134        } catch (NullPointerException ex) {
4135            Rlog.e(TAG, "hasCarrierPrivileges NPE", ex);
4136        }
4137        return false;
4138    }
4139
4140    /**
4141     * Override the branding for the current ICCID.
4142     *
4143     * Once set, whenever the SIM is present in the device, the service
4144     * provider name (SPN) and the operator name will both be replaced by the
4145     * brand value input. To unset the value, the same function should be
4146     * called with a null brand value.
4147     *
4148     * <p>Requires that the calling app has carrier privileges.
4149     * @see #hasCarrierPrivileges
4150     *
4151     * @param brand The brand name to display/set.
4152     * @return true if the operation was executed correctly.
4153     */
4154    public boolean setOperatorBrandOverride(String brand) {
4155        return setOperatorBrandOverride(getDefaultSubscription(), brand);
4156    }
4157
4158    /**
4159     * Override the branding for the current ICCID.
4160     *
4161     * Once set, whenever the SIM is present in the device, the service
4162     * provider name (SPN) and the operator name will both be replaced by the
4163     * brand value input. To unset the value, the same function should be
4164     * called with a null brand value.
4165     *
4166     * <p>Requires that the calling app has carrier privileges.
4167     * @see #hasCarrierPrivileges
4168     *
4169     * @param subId The subscription to use.
4170     * @param brand The brand name to display/set.
4171     * @return true if the operation was executed correctly.
4172     */
4173    public boolean setOperatorBrandOverride(int subId, String brand) {
4174        try {
4175            ITelephony telephony = getITelephony();
4176            if (telephony != null)
4177                return telephony.setOperatorBrandOverride(subId, brand);
4178        } catch (RemoteException ex) {
4179            Rlog.e(TAG, "setOperatorBrandOverride RemoteException", ex);
4180        } catch (NullPointerException ex) {
4181            Rlog.e(TAG, "setOperatorBrandOverride NPE", ex);
4182        }
4183        return false;
4184    }
4185
4186    /**
4187     * Override the roaming preference for the current ICCID.
4188     *
4189     * Using this call, the carrier app (see #hasCarrierPrivileges) can override
4190     * the platform's notion of a network operator being considered roaming or not.
4191     * The change only affects the ICCID that was active when this call was made.
4192     *
4193     * If null is passed as any of the input, the corresponding value is deleted.
4194     *
4195     * <p>Requires that the caller have carrier privilege. See #hasCarrierPrivileges.
4196     *
4197     * @param gsmRoamingList - List of MCCMNCs to be considered roaming for 3GPP RATs.
4198     * @param gsmNonRoamingList - List of MCCMNCs to be considered not roaming for 3GPP RATs.
4199     * @param cdmaRoamingList - List of SIDs to be considered roaming for 3GPP2 RATs.
4200     * @param cdmaNonRoamingList - List of SIDs to be considered not roaming for 3GPP2 RATs.
4201     * @return true if the operation was executed correctly.
4202     *
4203     * @hide
4204     */
4205    public boolean setRoamingOverride(List<String> gsmRoamingList,
4206            List<String> gsmNonRoamingList, List<String> cdmaRoamingList,
4207            List<String> cdmaNonRoamingList) {
4208        return setRoamingOverride(getDefaultSubscription(), gsmRoamingList, gsmNonRoamingList,
4209                cdmaRoamingList, cdmaNonRoamingList);
4210    }
4211
4212    /**
4213     * Override the roaming preference for the current ICCID.
4214     *
4215     * Using this call, the carrier app (see #hasCarrierPrivileges) can override
4216     * the platform's notion of a network operator being considered roaming or not.
4217     * The change only affects the ICCID that was active when this call was made.
4218     *
4219     * If null is passed as any of the input, the corresponding value is deleted.
4220     *
4221     * <p>Requires that the caller have carrier privilege. See #hasCarrierPrivileges.
4222     *
4223     * @param subId for which the roaming overrides apply.
4224     * @param gsmRoamingList - List of MCCMNCs to be considered roaming for 3GPP RATs.
4225     * @param gsmNonRoamingList - List of MCCMNCs to be considered not roaming for 3GPP RATs.
4226     * @param cdmaRoamingList - List of SIDs to be considered roaming for 3GPP2 RATs.
4227     * @param cdmaNonRoamingList - List of SIDs to be considered not roaming for 3GPP2 RATs.
4228     * @return true if the operation was executed correctly.
4229     *
4230     * @hide
4231     */
4232    public boolean setRoamingOverride(int subId, List<String> gsmRoamingList,
4233            List<String> gsmNonRoamingList, List<String> cdmaRoamingList,
4234            List<String> cdmaNonRoamingList) {
4235        try {
4236            ITelephony telephony = getITelephony();
4237            if (telephony != null)
4238                return telephony.setRoamingOverride(subId, gsmRoamingList, gsmNonRoamingList,
4239                        cdmaRoamingList, cdmaNonRoamingList);
4240        } catch (RemoteException ex) {
4241            Rlog.e(TAG, "setRoamingOverride RemoteException", ex);
4242        } catch (NullPointerException ex) {
4243            Rlog.e(TAG, "setRoamingOverride NPE", ex);
4244        }
4245        return false;
4246    }
4247
4248    /**
4249     * Expose the rest of ITelephony to @SystemApi
4250     */
4251
4252    /** @hide */
4253    @SystemApi
4254    public String getCdmaMdn() {
4255        return getCdmaMdn(getDefaultSubscription());
4256    }
4257
4258    /** @hide */
4259    @SystemApi
4260    public String getCdmaMdn(int subId) {
4261        try {
4262            ITelephony telephony = getITelephony();
4263            if (telephony == null)
4264                return null;
4265            return telephony.getCdmaMdn(subId);
4266        } catch (RemoteException ex) {
4267            return null;
4268        } catch (NullPointerException ex) {
4269            return null;
4270        }
4271    }
4272
4273    /** @hide */
4274    @SystemApi
4275    public String getCdmaMin() {
4276        return getCdmaMin(getDefaultSubscription());
4277    }
4278
4279    /** @hide */
4280    @SystemApi
4281    public String getCdmaMin(int subId) {
4282        try {
4283            ITelephony telephony = getITelephony();
4284            if (telephony == null)
4285                return null;
4286            return telephony.getCdmaMin(subId);
4287        } catch (RemoteException ex) {
4288            return null;
4289        } catch (NullPointerException ex) {
4290            return null;
4291        }
4292    }
4293
4294    /** @hide */
4295    @SystemApi
4296    public int checkCarrierPrivilegesForPackage(String pkgName) {
4297        try {
4298            ITelephony telephony = getITelephony();
4299            if (telephony != null)
4300                return telephony.checkCarrierPrivilegesForPackage(pkgName);
4301        } catch (RemoteException ex) {
4302            Rlog.e(TAG, "checkCarrierPrivilegesForPackage RemoteException", ex);
4303        } catch (NullPointerException ex) {
4304            Rlog.e(TAG, "checkCarrierPrivilegesForPackage NPE", ex);
4305        }
4306        return CARRIER_PRIVILEGE_STATUS_NO_ACCESS;
4307    }
4308
4309    /** @hide */
4310    @SystemApi
4311    public int checkCarrierPrivilegesForPackageAnyPhone(String pkgName) {
4312        try {
4313            ITelephony telephony = getITelephony();
4314            if (telephony != null)
4315                return telephony.checkCarrierPrivilegesForPackageAnyPhone(pkgName);
4316        } catch (RemoteException ex) {
4317            Rlog.e(TAG, "checkCarrierPrivilegesForPackageAnyPhone RemoteException", ex);
4318        } catch (NullPointerException ex) {
4319            Rlog.e(TAG, "checkCarrierPrivilegesForPackageAnyPhone NPE", ex);
4320        }
4321        return CARRIER_PRIVILEGE_STATUS_NO_ACCESS;
4322    }
4323
4324    /** @hide */
4325    @SystemApi
4326    public List<String> getCarrierPackageNamesForIntent(Intent intent) {
4327        return getCarrierPackageNamesForIntentAndPhone(intent, getDefaultPhone());
4328    }
4329
4330    /** @hide */
4331    @SystemApi
4332    public List<String> getCarrierPackageNamesForIntentAndPhone(Intent intent, int phoneId) {
4333        try {
4334            ITelephony telephony = getITelephony();
4335            if (telephony != null)
4336                return telephony.getCarrierPackageNamesForIntentAndPhone(intent, phoneId);
4337        } catch (RemoteException ex) {
4338            Rlog.e(TAG, "getCarrierPackageNamesForIntentAndPhone RemoteException", ex);
4339        } catch (NullPointerException ex) {
4340            Rlog.e(TAG, "getCarrierPackageNamesForIntentAndPhone NPE", ex);
4341        }
4342        return null;
4343    }
4344
4345    /** @hide */
4346    public List<String> getPackagesWithCarrierPrivileges() {
4347        try {
4348            ITelephony telephony = getITelephony();
4349            if (telephony != null) {
4350                return telephony.getPackagesWithCarrierPrivileges();
4351            }
4352        } catch (RemoteException ex) {
4353            Rlog.e(TAG, "getPackagesWithCarrierPrivileges RemoteException", ex);
4354        } catch (NullPointerException ex) {
4355            Rlog.e(TAG, "getPackagesWithCarrierPrivileges NPE", ex);
4356        }
4357        return Collections.EMPTY_LIST;
4358    }
4359
4360    /** @hide */
4361    @SystemApi
4362    public void dial(String number) {
4363        try {
4364            ITelephony telephony = getITelephony();
4365            if (telephony != null)
4366                telephony.dial(number);
4367        } catch (RemoteException e) {
4368            Log.e(TAG, "Error calling ITelephony#dial", e);
4369        }
4370    }
4371
4372    /** @hide */
4373    @SystemApi
4374    public void call(String callingPackage, String number) {
4375        try {
4376            ITelephony telephony = getITelephony();
4377            if (telephony != null)
4378                telephony.call(callingPackage, number);
4379        } catch (RemoteException e) {
4380            Log.e(TAG, "Error calling ITelephony#call", e);
4381        }
4382    }
4383
4384    /** @hide */
4385    @SystemApi
4386    public boolean endCall() {
4387        try {
4388            ITelephony telephony = getITelephony();
4389            if (telephony != null)
4390                return telephony.endCall();
4391        } catch (RemoteException e) {
4392            Log.e(TAG, "Error calling ITelephony#endCall", e);
4393        }
4394        return false;
4395    }
4396
4397    /** @hide */
4398    @SystemApi
4399    public void answerRingingCall() {
4400        try {
4401            ITelephony telephony = getITelephony();
4402            if (telephony != null)
4403                telephony.answerRingingCall();
4404        } catch (RemoteException e) {
4405            Log.e(TAG, "Error calling ITelephony#answerRingingCall", e);
4406        }
4407    }
4408
4409    /** @hide */
4410    @SystemApi
4411    public void silenceRinger() {
4412        try {
4413            getTelecomService().silenceRinger(getOpPackageName());
4414        } catch (RemoteException e) {
4415            Log.e(TAG, "Error calling ITelecomService#silenceRinger", e);
4416        }
4417    }
4418
4419    /** @hide */
4420    @SystemApi
4421    public boolean isOffhook() {
4422        try {
4423            ITelephony telephony = getITelephony();
4424            if (telephony != null)
4425                return telephony.isOffhook(getOpPackageName());
4426        } catch (RemoteException e) {
4427            Log.e(TAG, "Error calling ITelephony#isOffhook", e);
4428        }
4429        return false;
4430    }
4431
4432    /** @hide */
4433    @SystemApi
4434    public boolean isRinging() {
4435        try {
4436            ITelephony telephony = getITelephony();
4437            if (telephony != null)
4438                return telephony.isRinging(getOpPackageName());
4439        } catch (RemoteException e) {
4440            Log.e(TAG, "Error calling ITelephony#isRinging", e);
4441        }
4442        return false;
4443    }
4444
4445    /** @hide */
4446    @SystemApi
4447    public boolean isIdle() {
4448        try {
4449            ITelephony telephony = getITelephony();
4450            if (telephony != null)
4451                return telephony.isIdle(getOpPackageName());
4452        } catch (RemoteException e) {
4453            Log.e(TAG, "Error calling ITelephony#isIdle", e);
4454        }
4455        return true;
4456    }
4457
4458    /** @hide */
4459    @SystemApi
4460    public boolean isRadioOn() {
4461        try {
4462            ITelephony telephony = getITelephony();
4463            if (telephony != null)
4464                return telephony.isRadioOn(getOpPackageName());
4465        } catch (RemoteException e) {
4466            Log.e(TAG, "Error calling ITelephony#isRadioOn", e);
4467        }
4468        return false;
4469    }
4470
4471    /** @hide */
4472    @SystemApi
4473    public boolean supplyPin(String pin) {
4474        try {
4475            ITelephony telephony = getITelephony();
4476            if (telephony != null)
4477                return telephony.supplyPin(pin);
4478        } catch (RemoteException e) {
4479            Log.e(TAG, "Error calling ITelephony#supplyPin", e);
4480        }
4481        return false;
4482    }
4483
4484    /** @hide */
4485    @SystemApi
4486    public boolean supplyPuk(String puk, String pin) {
4487        try {
4488            ITelephony telephony = getITelephony();
4489            if (telephony != null)
4490                return telephony.supplyPuk(puk, pin);
4491        } catch (RemoteException e) {
4492            Log.e(TAG, "Error calling ITelephony#supplyPuk", e);
4493        }
4494        return false;
4495    }
4496
4497    /** @hide */
4498    @SystemApi
4499    public int[] supplyPinReportResult(String pin) {
4500        try {
4501            ITelephony telephony = getITelephony();
4502            if (telephony != null)
4503                return telephony.supplyPinReportResult(pin);
4504        } catch (RemoteException e) {
4505            Log.e(TAG, "Error calling ITelephony#supplyPinReportResult", e);
4506        }
4507        return new int[0];
4508    }
4509
4510    /** @hide */
4511    @SystemApi
4512    public int[] supplyPukReportResult(String puk, String pin) {
4513        try {
4514            ITelephony telephony = getITelephony();
4515            if (telephony != null)
4516                return telephony.supplyPukReportResult(puk, pin);
4517        } catch (RemoteException e) {
4518            Log.e(TAG, "Error calling ITelephony#]", e);
4519        }
4520        return new int[0];
4521    }
4522
4523    /** @hide */
4524    @SystemApi
4525    public boolean handlePinMmi(String dialString) {
4526        try {
4527            ITelephony telephony = getITelephony();
4528            if (telephony != null)
4529                return telephony.handlePinMmi(dialString);
4530        } catch (RemoteException e) {
4531            Log.e(TAG, "Error calling ITelephony#handlePinMmi", e);
4532        }
4533        return false;
4534    }
4535
4536    /** @hide */
4537    @SystemApi
4538    public boolean handlePinMmiForSubscriber(int subId, String dialString) {
4539        try {
4540            ITelephony telephony = getITelephony();
4541            if (telephony != null)
4542                return telephony.handlePinMmiForSubscriber(subId, dialString);
4543        } catch (RemoteException e) {
4544            Log.e(TAG, "Error calling ITelephony#handlePinMmi", e);
4545        }
4546        return false;
4547    }
4548
4549    /** @hide */
4550    @SystemApi
4551    public void toggleRadioOnOff() {
4552        try {
4553            ITelephony telephony = getITelephony();
4554            if (telephony != null)
4555                telephony.toggleRadioOnOff();
4556        } catch (RemoteException e) {
4557            Log.e(TAG, "Error calling ITelephony#toggleRadioOnOff", e);
4558        }
4559    }
4560
4561    /** @hide */
4562    @SystemApi
4563    public boolean setRadio(boolean turnOn) {
4564        try {
4565            ITelephony telephony = getITelephony();
4566            if (telephony != null)
4567                return telephony.setRadio(turnOn);
4568        } catch (RemoteException e) {
4569            Log.e(TAG, "Error calling ITelephony#setRadio", e);
4570        }
4571        return false;
4572    }
4573
4574    /** @hide */
4575    @SystemApi
4576    public boolean setRadioPower(boolean turnOn) {
4577        try {
4578            ITelephony telephony = getITelephony();
4579            if (telephony != null)
4580                return telephony.setRadioPower(turnOn);
4581        } catch (RemoteException e) {
4582            Log.e(TAG, "Error calling ITelephony#setRadioPower", e);
4583        }
4584        return false;
4585    }
4586
4587    /** @hide */
4588    @SystemApi
4589    public void updateServiceLocation() {
4590        try {
4591            ITelephony telephony = getITelephony();
4592            if (telephony != null)
4593                telephony.updateServiceLocation();
4594        } catch (RemoteException e) {
4595            Log.e(TAG, "Error calling ITelephony#updateServiceLocation", e);
4596        }
4597    }
4598
4599    /** @hide */
4600    @SystemApi
4601    public boolean enableDataConnectivity() {
4602        try {
4603            ITelephony telephony = getITelephony();
4604            if (telephony != null)
4605                return telephony.enableDataConnectivity();
4606        } catch (RemoteException e) {
4607            Log.e(TAG, "Error calling ITelephony#enableDataConnectivity", e);
4608        }
4609        return false;
4610    }
4611
4612    /** @hide */
4613    @SystemApi
4614    public boolean disableDataConnectivity() {
4615        try {
4616            ITelephony telephony = getITelephony();
4617            if (telephony != null)
4618                return telephony.disableDataConnectivity();
4619        } catch (RemoteException e) {
4620            Log.e(TAG, "Error calling ITelephony#disableDataConnectivity", e);
4621        }
4622        return false;
4623    }
4624
4625    /** @hide */
4626    @SystemApi
4627    public boolean isDataConnectivityPossible() {
4628        try {
4629            ITelephony telephony = getITelephony();
4630            if (telephony != null)
4631                return telephony.isDataConnectivityPossible();
4632        } catch (RemoteException e) {
4633            Log.e(TAG, "Error calling ITelephony#isDataConnectivityPossible", e);
4634        }
4635        return false;
4636    }
4637
4638    /** @hide */
4639    @SystemApi
4640    public boolean needsOtaServiceProvisioning() {
4641        try {
4642            ITelephony telephony = getITelephony();
4643            if (telephony != null)
4644                return telephony.needsOtaServiceProvisioning();
4645        } catch (RemoteException e) {
4646            Log.e(TAG, "Error calling ITelephony#needsOtaServiceProvisioning", e);
4647        }
4648        return false;
4649    }
4650
4651    /** @hide */
4652    @SystemApi
4653    public void setDataEnabled(boolean enable) {
4654        setDataEnabled(SubscriptionManager.getDefaultDataSubscriptionId(), enable);
4655    }
4656
4657    /** @hide */
4658    @SystemApi
4659    public void setDataEnabled(int subId, boolean enable) {
4660        try {
4661            Log.d(TAG, "setDataEnabled: enabled=" + enable);
4662            ITelephony telephony = getITelephony();
4663            if (telephony != null)
4664                telephony.setDataEnabled(subId, enable);
4665        } catch (RemoteException e) {
4666            Log.e(TAG, "Error calling ITelephony#setDataEnabled", e);
4667        }
4668    }
4669
4670    /** @hide */
4671    @SystemApi
4672    public boolean getDataEnabled() {
4673        return getDataEnabled(SubscriptionManager.getDefaultDataSubscriptionId());
4674    }
4675
4676    /** @hide */
4677    @SystemApi
4678    public boolean getDataEnabled(int subId) {
4679        boolean retVal = false;
4680        try {
4681            ITelephony telephony = getITelephony();
4682            if (telephony != null)
4683                retVal = telephony.getDataEnabled(subId);
4684        } catch (RemoteException e) {
4685            Log.e(TAG, "Error calling ITelephony#getDataEnabled", e);
4686        } catch (NullPointerException e) {
4687        }
4688        return retVal;
4689    }
4690
4691    /**
4692     * Returns the result and response from RIL for oem request
4693     *
4694     * @param oemReq the data is sent to ril.
4695     * @param oemResp the respose data from RIL.
4696     * @return negative value request was not handled or get error
4697     *         0 request was handled succesfully, but no response data
4698     *         positive value success, data length of response
4699     * @hide
4700     */
4701    public int invokeOemRilRequestRaw(byte[] oemReq, byte[] oemResp) {
4702        try {
4703            ITelephony telephony = getITelephony();
4704            if (telephony != null)
4705                return telephony.invokeOemRilRequestRaw(oemReq, oemResp);
4706        } catch (RemoteException ex) {
4707        } catch (NullPointerException ex) {
4708        }
4709        return -1;
4710    }
4711
4712    /** @hide */
4713    @SystemApi
4714    public void enableVideoCalling(boolean enable) {
4715        try {
4716            ITelephony telephony = getITelephony();
4717            if (telephony != null)
4718                telephony.enableVideoCalling(enable);
4719        } catch (RemoteException e) {
4720            Log.e(TAG, "Error calling ITelephony#enableVideoCalling", e);
4721        }
4722    }
4723
4724    /** @hide */
4725    @SystemApi
4726    public boolean isVideoCallingEnabled() {
4727        try {
4728            ITelephony telephony = getITelephony();
4729            if (telephony != null)
4730                return telephony.isVideoCallingEnabled(getOpPackageName());
4731        } catch (RemoteException e) {
4732            Log.e(TAG, "Error calling ITelephony#isVideoCallingEnabled", e);
4733        }
4734        return false;
4735    }
4736
4737    /**
4738     * Whether the device supports configuring the DTMF tone length.
4739     *
4740     * @return {@code true} if the DTMF tone length can be changed, and {@code false} otherwise.
4741     */
4742    public boolean canChangeDtmfToneLength() {
4743        try {
4744            ITelephony telephony = getITelephony();
4745            if (telephony != null) {
4746                return telephony.canChangeDtmfToneLength();
4747            }
4748        } catch (RemoteException e) {
4749            Log.e(TAG, "Error calling ITelephony#canChangeDtmfToneLength", e);
4750        } catch (SecurityException e) {
4751            Log.e(TAG, "Permission error calling ITelephony#canChangeDtmfToneLength", e);
4752        }
4753        return false;
4754    }
4755
4756    /**
4757     * Whether the device is a world phone.
4758     *
4759     * @return {@code true} if the device is a world phone, and {@code false} otherwise.
4760     */
4761    public boolean isWorldPhone() {
4762        try {
4763            ITelephony telephony = getITelephony();
4764            if (telephony != null) {
4765                return telephony.isWorldPhone();
4766            }
4767        } catch (RemoteException e) {
4768            Log.e(TAG, "Error calling ITelephony#isWorldPhone", e);
4769        } catch (SecurityException e) {
4770            Log.e(TAG, "Permission error calling ITelephony#isWorldPhone", e);
4771        }
4772        return false;
4773    }
4774
4775    /**
4776     * Whether the phone supports TTY mode.
4777     *
4778     * @return {@code true} if the device supports TTY mode, and {@code false} otherwise.
4779     */
4780    public boolean isTtyModeSupported() {
4781        try {
4782            ITelephony telephony = getITelephony();
4783            if (telephony != null) {
4784                return telephony.isTtyModeSupported();
4785            }
4786        } catch (RemoteException e) {
4787            Log.e(TAG, "Error calling ITelephony#isTtyModeSupported", e);
4788        } catch (SecurityException e) {
4789            Log.e(TAG, "Permission error calling ITelephony#isTtyModeSupported", e);
4790        }
4791        return false;
4792    }
4793
4794    /**
4795     * Whether the phone supports hearing aid compatibility.
4796     *
4797     * @return {@code true} if the device supports hearing aid compatibility, and {@code false}
4798     * otherwise.
4799     */
4800    public boolean isHearingAidCompatibilitySupported() {
4801        try {
4802            ITelephony telephony = getITelephony();
4803            if (telephony != null) {
4804                return telephony.isHearingAidCompatibilitySupported();
4805            }
4806        } catch (RemoteException e) {
4807            Log.e(TAG, "Error calling ITelephony#isHearingAidCompatibilitySupported", e);
4808        } catch (SecurityException e) {
4809            Log.e(TAG, "Permission error calling ITelephony#isHearingAidCompatibilitySupported", e);
4810        }
4811        return false;
4812    }
4813
4814    /**
4815     * This function retrieves value for setting "name+subId", and if that is not found
4816     * retrieves value for setting "name", and if that is not found throws
4817     * SettingNotFoundException
4818     *
4819     * @hide */
4820    public static int getIntWithSubId(ContentResolver cr, String name, int subId)
4821            throws SettingNotFoundException {
4822        try {
4823            return Settings.Global.getInt(cr, name + subId);
4824        } catch (SettingNotFoundException e) {
4825            try {
4826                int val = Settings.Global.getInt(cr, name);
4827                Settings.Global.putInt(cr, name + subId, val);
4828
4829                /* We are now moving from 'setting' to 'setting+subId', and using the value stored
4830                 * for 'setting' as default. Reset the default (since it may have a user set
4831                 * value). */
4832                int default_val = val;
4833                if (name.equals(Settings.Global.MOBILE_DATA)) {
4834                    default_val = "true".equalsIgnoreCase(
4835                            SystemProperties.get("ro.com.android.mobiledata", "true")) ? 1 : 0;
4836                } else if (name.equals(Settings.Global.DATA_ROAMING)) {
4837                    default_val = "true".equalsIgnoreCase(
4838                            SystemProperties.get("ro.com.android.dataroaming", "false")) ? 1 : 0;
4839                }
4840
4841                if (default_val != val) {
4842                    Settings.Global.putInt(cr, name, default_val);
4843                }
4844
4845                return val;
4846            } catch (SettingNotFoundException exc) {
4847                throw new SettingNotFoundException(name);
4848            }
4849        }
4850    }
4851
4852   /**
4853    * Returns the IMS Registration Status
4854    * @hide
4855    */
4856   public boolean isImsRegistered() {
4857       try {
4858           ITelephony telephony = getITelephony();
4859           if (telephony == null)
4860               return false;
4861           return telephony.isImsRegistered();
4862       } catch (RemoteException ex) {
4863           return false;
4864       } catch (NullPointerException ex) {
4865           return false;
4866       }
4867   }
4868
4869    /**
4870     * Returns the Status of Volte
4871     * @hide
4872     */
4873    public boolean isVolteAvailable() {
4874       try {
4875           return getITelephony().isVolteAvailable();
4876       } catch (RemoteException ex) {
4877           return false;
4878       } catch (NullPointerException ex) {
4879           return false;
4880       }
4881   }
4882
4883    /**
4884     * Returns the Status of video telephony (VT)
4885     * @hide
4886     */
4887    public boolean isVideoTelephonyAvailable() {
4888        try {
4889            return getITelephony().isVideoTelephonyAvailable();
4890        } catch (RemoteException ex) {
4891            return false;
4892        } catch (NullPointerException ex) {
4893            return false;
4894        }
4895    }
4896
4897    /**
4898     * Returns the Status of Wi-Fi Calling
4899     * @hide
4900     */
4901    public boolean isWifiCallingAvailable() {
4902       try {
4903           return getITelephony().isWifiCallingAvailable();
4904       } catch (RemoteException ex) {
4905           return false;
4906       } catch (NullPointerException ex) {
4907           return false;
4908       }
4909   }
4910
4911   /**
4912    * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC for the default phone.
4913    *
4914    * @hide
4915    */
4916    public void setSimOperatorNumeric(String numeric) {
4917        int phoneId = getDefaultPhone();
4918        setSimOperatorNumericForPhone(phoneId, numeric);
4919    }
4920
4921   /**
4922    * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC for the given phone.
4923    *
4924    * @hide
4925    */
4926    public void setSimOperatorNumericForPhone(int phoneId, String numeric) {
4927        setTelephonyProperty(phoneId,
4928                TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC, numeric);
4929    }
4930
4931    /**
4932     * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC for the default phone.
4933     *
4934     * @hide
4935     */
4936    public void setSimOperatorName(String name) {
4937        int phoneId = getDefaultPhone();
4938        setSimOperatorNameForPhone(phoneId, name);
4939    }
4940
4941    /**
4942     * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC for the given phone.
4943     *
4944     * @hide
4945     */
4946    public void setSimOperatorNameForPhone(int phoneId, String name) {
4947        setTelephonyProperty(phoneId,
4948                TelephonyProperties.PROPERTY_ICC_OPERATOR_ALPHA, name);
4949    }
4950
4951   /**
4952    * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_ISO_COUNTRY for the default phone.
4953    *
4954    * @hide
4955    */
4956    public void setSimCountryIso(String iso) {
4957        int phoneId = getDefaultPhone();
4958        setSimCountryIsoForPhone(phoneId, iso);
4959    }
4960
4961   /**
4962    * Set TelephonyProperties.PROPERTY_ICC_OPERATOR_ISO_COUNTRY for the given phone.
4963    *
4964    * @hide
4965    */
4966    public void setSimCountryIsoForPhone(int phoneId, String iso) {
4967        setTelephonyProperty(phoneId,
4968                TelephonyProperties.PROPERTY_ICC_OPERATOR_ISO_COUNTRY, iso);
4969    }
4970
4971    /**
4972     * Set TelephonyProperties.PROPERTY_SIM_STATE for the default phone.
4973     *
4974     * @hide
4975     */
4976    public void setSimState(String state) {
4977        int phoneId = getDefaultPhone();
4978        setSimStateForPhone(phoneId, state);
4979    }
4980
4981    /**
4982     * Set TelephonyProperties.PROPERTY_SIM_STATE for the given phone.
4983     *
4984     * @hide
4985     */
4986    public void setSimStateForPhone(int phoneId, String state) {
4987        setTelephonyProperty(phoneId,
4988                TelephonyProperties.PROPERTY_SIM_STATE, state);
4989    }
4990
4991    /**
4992     * Set baseband version for the default phone.
4993     *
4994     * @param version baseband version
4995     * @hide
4996     */
4997    public void setBasebandVersion(String version) {
4998        int phoneId = getDefaultPhone();
4999        setBasebandVersionForPhone(phoneId, version);
5000    }
5001
5002    /**
5003     * Set baseband version by phone id.
5004     *
5005     * @param phoneId for which baseband version is set
5006     * @param version baseband version
5007     * @hide
5008     */
5009    public void setBasebandVersionForPhone(int phoneId, String version) {
5010        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5011            String prop = TelephonyProperties.PROPERTY_BASEBAND_VERSION +
5012                    ((phoneId == 0) ? "" : Integer.toString(phoneId));
5013            SystemProperties.set(prop, version);
5014        }
5015    }
5016
5017    /**
5018     * Set phone type for the default phone.
5019     *
5020     * @param type phone type
5021     *
5022     * @hide
5023     */
5024    public void setPhoneType(int type) {
5025        int phoneId = getDefaultPhone();
5026        setPhoneType(phoneId, type);
5027    }
5028
5029    /**
5030     * Set phone type by phone id.
5031     *
5032     * @param phoneId for which phone type is set
5033     * @param type phone type
5034     *
5035     * @hide
5036     */
5037    public void setPhoneType(int phoneId, int type) {
5038        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5039            TelephonyManager.setTelephonyProperty(phoneId,
5040                    TelephonyProperties.CURRENT_ACTIVE_PHONE, String.valueOf(type));
5041        }
5042    }
5043
5044    /**
5045     * Get OTASP number schema for the default phone.
5046     *
5047     * @param defaultValue default value
5048     * @return OTA SP number schema
5049     *
5050     * @hide
5051     */
5052    public String getOtaSpNumberSchema(String defaultValue) {
5053        int phoneId = getDefaultPhone();
5054        return getOtaSpNumberSchemaForPhone(phoneId, defaultValue);
5055    }
5056
5057    /**
5058     * Get OTASP number schema by phone id.
5059     *
5060     * @param phoneId for which OTA SP number schema is get
5061     * @param defaultValue default value
5062     * @return OTA SP number schema
5063     *
5064     * @hide
5065     */
5066    public String getOtaSpNumberSchemaForPhone(int phoneId, String defaultValue) {
5067        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5068            return TelephonyManager.getTelephonyProperty(phoneId,
5069                    TelephonyProperties.PROPERTY_OTASP_NUM_SCHEMA, defaultValue);
5070        }
5071
5072        return defaultValue;
5073    }
5074
5075    /**
5076     * Get SMS receive capable from system property for the default phone.
5077     *
5078     * @param defaultValue default value
5079     * @return SMS receive capable
5080     *
5081     * @hide
5082     */
5083    public boolean getSmsReceiveCapable(boolean defaultValue) {
5084        int phoneId = getDefaultPhone();
5085        return getSmsReceiveCapableForPhone(phoneId, defaultValue);
5086    }
5087
5088    /**
5089     * Get SMS receive capable from system property by phone id.
5090     *
5091     * @param phoneId for which SMS receive capable is get
5092     * @param defaultValue default value
5093     * @return SMS receive capable
5094     *
5095     * @hide
5096     */
5097    public boolean getSmsReceiveCapableForPhone(int phoneId, boolean defaultValue) {
5098        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5099            return Boolean.valueOf(TelephonyManager.getTelephonyProperty(phoneId,
5100                    TelephonyProperties.PROPERTY_SMS_RECEIVE, String.valueOf(defaultValue)));
5101        }
5102
5103        return defaultValue;
5104    }
5105
5106    /**
5107     * Get SMS send capable from system property for the default phone.
5108     *
5109     * @param defaultValue default value
5110     * @return SMS send capable
5111     *
5112     * @hide
5113     */
5114    public boolean getSmsSendCapable(boolean defaultValue) {
5115        int phoneId = getDefaultPhone();
5116        return getSmsSendCapableForPhone(phoneId, defaultValue);
5117    }
5118
5119    /**
5120     * Get SMS send capable from system property by phone id.
5121     *
5122     * @param phoneId for which SMS send capable is get
5123     * @param defaultValue default value
5124     * @return SMS send capable
5125     *
5126     * @hide
5127     */
5128    public boolean getSmsSendCapableForPhone(int phoneId, boolean defaultValue) {
5129        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5130            return Boolean.valueOf(TelephonyManager.getTelephonyProperty(phoneId,
5131                    TelephonyProperties.PROPERTY_SMS_SEND, String.valueOf(defaultValue)));
5132        }
5133
5134        return defaultValue;
5135    }
5136
5137    /**
5138     * Set the alphabetic name of current registered operator.
5139     * @param name the alphabetic name of current registered operator.
5140     * @hide
5141     */
5142    public void setNetworkOperatorName(String name) {
5143        int phoneId = getDefaultPhone();
5144        setNetworkOperatorNameForPhone(phoneId, name);
5145    }
5146
5147    /**
5148     * Set the alphabetic name of current registered operator.
5149     * @param phoneId which phone you want to set
5150     * @param name the alphabetic name of current registered operator.
5151     * @hide
5152     */
5153    public void setNetworkOperatorNameForPhone(int phoneId, String name) {
5154        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5155            setTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_ALPHA, name);
5156        }
5157    }
5158
5159    /**
5160     * Set the numeric name (MCC+MNC) of current registered operator.
5161     * @param operator the numeric name (MCC+MNC) of current registered operator
5162     * @hide
5163     */
5164    public void setNetworkOperatorNumeric(String numeric) {
5165        int phoneId = getDefaultPhone();
5166        setNetworkOperatorNumericForPhone(phoneId, numeric);
5167    }
5168
5169    /**
5170     * Set the numeric name (MCC+MNC) of current registered operator.
5171     * @param phoneId for which phone type is set
5172     * @param operator the numeric name (MCC+MNC) of current registered operator
5173     * @hide
5174     */
5175    public void setNetworkOperatorNumericForPhone(int phoneId, String numeric) {
5176        setTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_NUMERIC, numeric);
5177    }
5178
5179    /**
5180     * Set roaming state of the current network, for GSM purposes.
5181     * @param isRoaming is network in romaing state or not
5182     * @hide
5183     */
5184    public void setNetworkRoaming(boolean isRoaming) {
5185        int phoneId = getDefaultPhone();
5186        setNetworkRoamingForPhone(phoneId, isRoaming);
5187    }
5188
5189    /**
5190     * Set roaming state of the current network, for GSM purposes.
5191     * @param phoneId which phone you want to set
5192     * @param isRoaming is network in romaing state or not
5193     * @hide
5194     */
5195    public void setNetworkRoamingForPhone(int phoneId, boolean isRoaming) {
5196        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5197            setTelephonyProperty(phoneId, TelephonyProperties.PROPERTY_OPERATOR_ISROAMING,
5198                    isRoaming ? "true" : "false");
5199        }
5200    }
5201
5202    /**
5203     * Set the ISO country code equivalent of the current registered
5204     * operator's MCC (Mobile Country Code).
5205     * @param iso the ISO country code equivalent of the current registered
5206     * @hide
5207     */
5208    public void setNetworkCountryIso(String iso) {
5209        int phoneId = getDefaultPhone();
5210        setNetworkCountryIsoForPhone(phoneId, iso);
5211    }
5212
5213    /**
5214     * Set the ISO country code equivalent of the current registered
5215     * operator's MCC (Mobile Country Code).
5216     * @param phoneId which phone you want to set
5217     * @param iso the ISO country code equivalent of the current registered
5218     * @hide
5219     */
5220    public void setNetworkCountryIsoForPhone(int phoneId, String iso) {
5221        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5222            setTelephonyProperty(phoneId,
5223                    TelephonyProperties.PROPERTY_OPERATOR_ISO_COUNTRY, iso);
5224        }
5225    }
5226
5227    /**
5228     * Set the network type currently in use on the device for data transmission.
5229     * @param type the network type currently in use on the device for data transmission
5230     * @hide
5231     */
5232    public void setDataNetworkType(int type) {
5233        int phoneId = getDefaultPhone();
5234        setDataNetworkTypeForPhone(phoneId, type);
5235    }
5236
5237    /**
5238     * Set the network type currently in use on the device for data transmission.
5239     * @param phoneId which phone you want to set
5240     * @param type the network type currently in use on the device for data transmission
5241     * @hide
5242     */
5243    public void setDataNetworkTypeForPhone(int phoneId, int type) {
5244        if (SubscriptionManager.isValidPhoneId(phoneId)) {
5245            setTelephonyProperty(phoneId,
5246                    TelephonyProperties.PROPERTY_DATA_NETWORK_TYPE,
5247                    ServiceState.rilRadioTechnologyToString(type));
5248        }
5249    }
5250
5251    /**
5252     * Returns the subscription ID for the given phone account.
5253     * @hide
5254     */
5255    public int getSubIdForPhoneAccount(PhoneAccount phoneAccount) {
5256        int retval = SubscriptionManager.INVALID_SUBSCRIPTION_ID;
5257        try {
5258            ITelephony service = getITelephony();
5259            if (service != null) {
5260                retval = service.getSubIdForPhoneAccount(phoneAccount);
5261            }
5262        } catch (RemoteException e) {
5263        }
5264
5265        return retval;
5266    }
5267
5268    /**
5269     * Resets telephony manager settings back to factory defaults.
5270     *
5271     * @hide
5272     */
5273    public void factoryReset(int subId) {
5274        try {
5275            Log.d(TAG, "factoryReset: subId=" + subId);
5276            ITelephony telephony = getITelephony();
5277            if (telephony != null)
5278                telephony.factoryReset(subId);
5279        } catch (RemoteException e) {
5280        }
5281    }
5282
5283
5284    /** @hide */
5285    public String getLocaleFromDefaultSim() {
5286        try {
5287            final ITelephony telephony = getITelephony();
5288            if (telephony != null) {
5289                return telephony.getLocaleFromDefaultSim();
5290            }
5291        } catch (RemoteException ex) {
5292        }
5293        return null;
5294    }
5295
5296    /**
5297     * Requests the modem activity info. The recipient will place the result
5298     * in `result`.
5299     * @param result The object on which the recipient will send the resulting
5300     * {@link android.telephony.ModemActivityInfo} object.
5301     * @hide
5302     */
5303    public void requestModemActivityInfo(ResultReceiver result) {
5304        try {
5305            ITelephony service = getITelephony();
5306            if (service != null) {
5307                service.requestModemActivityInfo(result);
5308                return;
5309            }
5310        } catch (RemoteException e) {
5311            Log.e(TAG, "Error calling ITelephony#getModemActivityInfo", e);
5312        }
5313        result.send(0, null);
5314    }
5315
5316    /**
5317     * Returns the service state information on specified subscription. Callers require
5318     * either READ_PRIVILEGED_PHONE_STATE or READ_PHONE_STATE to retrieve the information.
5319     * @hide
5320     */
5321    public ServiceState getServiceStateForSubscriber(int subId) {
5322        try {
5323            ITelephony service = getITelephony();
5324            if (service != null) {
5325                return service.getServiceStateForSubscriber(subId, getOpPackageName());
5326            }
5327        } catch (RemoteException e) {
5328            Log.e(TAG, "Error calling ITelephony#getServiceStateForSubscriber", e);
5329        }
5330        return null;
5331    }
5332
5333    /**
5334     * Returns the URI for the per-account voicemail ringtone set in Phone settings.
5335     *
5336     * @param accountHandle The handle for the {@link PhoneAccount} for which to retrieve the
5337     * voicemail ringtone.
5338     * @return The URI for the ringtone to play when receiving a voicemail from a specific
5339     * PhoneAccount.
5340     */
5341    public Uri getVoicemailRingtoneUri(PhoneAccountHandle accountHandle) {
5342        try {
5343            ITelephony service = getITelephony();
5344            if (service != null) {
5345                return service.getVoicemailRingtoneUri(accountHandle);
5346            }
5347        } catch (RemoteException e) {
5348            Log.e(TAG, "Error calling ITelephony#getVoicemailRingtoneUri", e);
5349        }
5350        return null;
5351    }
5352
5353    /**
5354     * Returns whether vibration is set for voicemail notification in Phone settings.
5355     *
5356     * @param accountHandle The handle for the {@link PhoneAccount} for which to retrieve the
5357     * voicemail vibration setting.
5358     * @return {@code true} if the vibration is set for this PhoneAccount, {@code false} otherwise.
5359     */
5360    public boolean isVoicemailVibrationEnabled(PhoneAccountHandle accountHandle) {
5361        try {
5362            ITelephony service = getITelephony();
5363            if (service != null) {
5364                return service.isVoicemailVibrationEnabled(accountHandle);
5365            }
5366        } catch (RemoteException e) {
5367            Log.e(TAG, "Error calling ITelephony#isVoicemailVibrationEnabled", e);
5368        }
5369        return false;
5370    }
5371
5372    /**
5373     * Return the application ID for the app type like {@link APPTYPE_CSIM}.
5374     *
5375     * Requires that the calling app has READ_PRIVILEGED_PHONE_STATE permission
5376     *
5377     * @param appType the uicc app type like {@link APPTYPE_CSIM}
5378     * @return Application ID for specificied app type or null if no uicc or error.
5379     * @hide
5380     */
5381    public String getAidForAppType(int appType) {
5382        return getAidForAppType(getDefaultSubscription(), appType);
5383    }
5384
5385    /**
5386     * Return the application ID for the app type like {@link APPTYPE_CSIM}.
5387     *
5388     * Requires that the calling app has READ_PRIVILEGED_PHONE_STATE permission
5389     *
5390     * @param subId the subscription ID that this request applies to.
5391     * @param appType the uicc app type, like {@link APPTYPE_CSIM}
5392     * @return Application ID for specificied app type or null if no uicc or error.
5393     * @hide
5394     */
5395    public String getAidForAppType(int subId, int appType) {
5396        try {
5397            ITelephony service = getITelephony();
5398            if (service != null) {
5399                return service.getAidForAppType(subId, appType);
5400            }
5401        } catch (RemoteException e) {
5402            Log.e(TAG, "Error calling ITelephony#getAidForAppType", e);
5403        }
5404        return null;
5405    }
5406
5407    /**
5408     * Return the Electronic Serial Number.
5409     *
5410     * Requires that the calling app has READ_PRIVILEGED_PHONE_STATE permission
5411     *
5412     * @return ESN or null if error.
5413     * @hide
5414     */
5415    public String getEsn() {
5416        return getEsn(getDefaultSubscription());
5417    }
5418
5419    /**
5420     * Return the Electronic Serial Number.
5421     *
5422     * Requires that the calling app has READ_PRIVILEGED_PHONE_STATE permission
5423     *
5424     * @param subId the subscription ID that this request applies to.
5425     * @return ESN or null if error.
5426     * @hide
5427     */
5428    public String getEsn(int subId) {
5429        try {
5430            ITelephony service = getITelephony();
5431            if (service != null) {
5432                return service.getEsn(subId);
5433            }
5434        } catch (RemoteException e) {
5435            Log.e(TAG, "Error calling ITelephony#getEsn", e);
5436        }
5437        return null;
5438    }
5439
5440}
5441