10825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville/*
20825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * Copyright (C) 2006 The Android Open Source Project
30825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville *
40825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * Licensed under the Apache License, Version 2.0 (the "License");
50825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * you may not use this file except in compliance with the License.
60825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * You may obtain a copy of the License at
70825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville *
80825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville *      http://www.apache.org/licenses/LICENSE-2.0
90825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville *
100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * Unless required by applicable law or agreed to in writing, software
110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * distributed under the License is distributed on an "AS IS" BASIS,
120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * See the License for the specific language governing permissions and
140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * limitations under the License.
150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville */
160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
170825495a331bb44df395a0cdb79fab85e68db5d5Wink Savillepackage com.android.internal.telephony.gsm;
180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
190825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.CommandException;
200825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.CommandsInterface;
210825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.DataConnectionTracker;
220825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.EventLogTags;
230825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.IccCard;
240825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.IccCardConstants;
250825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.IccCardStatus;
26f7a8133113daddcc48a41e451193afd3fcb35e16Wink Savilleimport com.android.internal.telephony.IccRecords;
270825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.MccTable;
280825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.Phone;
290825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.RestrictedState;
300825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.RILConstants;
310825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.ServiceStateTracker;
320825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.TelephonyIntents;
330825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport com.android.internal.telephony.TelephonyProperties;
34e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenkaimport com.android.internal.telephony.UiccCard;
35e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenkaimport com.android.internal.telephony.UiccCardApplication;
36e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenkaimport com.android.internal.telephony.IccCardApplicationStatus.AppState;
37e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenkaimport com.android.internal.telephony.uicc.UiccController;
380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
390825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.app.AlarmManager;
400825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.app.Notification;
410825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.app.NotificationManager;
420825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.app.PendingIntent;
430825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.BroadcastReceiver;
440825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.ContentResolver;
450825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.Context;
460825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.Intent;
470825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.IntentFilter;
480825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.content.res.Resources;
490825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.database.ContentObserver;
500825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.AsyncResult;
510825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.Handler;
520825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.Message;
530825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.PowerManager;
540825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.Registrant;
550825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.RegistrantList;
560825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.SystemClock;
570825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.os.SystemProperties;
587eff443d1f090abdbbd93eef9f265c74890920bcDianne Hackbornimport android.os.UserHandle;
590825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.provider.Settings;
600825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.provider.Settings.SettingNotFoundException;
61ef1d4bff9bbf7d967dbcace73f08910e14e367d0Wink Savilleimport android.telephony.CellInfo;
62ef1d4bff9bbf7d967dbcace73f08910e14e367d0Wink Savilleimport android.telephony.CellInfoGsm;
630825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.telephony.ServiceState;
640825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.telephony.SignalStrength;
650825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.telephony.gsm.GsmCellLocation;
660825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.text.TextUtils;
670825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.util.EventLog;
680825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.util.Log;
690825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport android.util.TimeUtils;
700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
710825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.io.FileDescriptor;
720825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.io.PrintWriter;
730825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.ArrayList;
740825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.Arrays;
750825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.Calendar;
760825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.Collection;
770825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.Date;
780825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.HashSet;
790825495a331bb44df395a0cdb79fab85e68db5d5Wink Savilleimport java.util.TimeZone;
800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville/**
820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville * {@hide}
830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville */
840825495a331bb44df395a0cdb79fab85e68db5d5Wink Savillefinal class GsmServiceStateTracker extends ServiceStateTracker {
850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final String LOG_TAG = "GSM";
860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final boolean DBG = true;
870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    GSMPhone phone;
890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    GsmCellLocation cellLoc;
900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    GsmCellLocation newCellLoc;
910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    int mPreferredNetworkType;
920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int gprsState = ServiceState.STATE_OUT_OF_SERVICE;
940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int newGPRSState = ServiceState.STATE_OUT_OF_SERVICE;
950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int mMaxDataCalls = 1;
960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int mNewMaxDataCalls = 1;
970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int mReasonDataDenied = -1;
980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int mNewReasonDataDenied = -1;
990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
1010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * GSM roaming status solely based on TS 27.007 7.2 CREG. Only used by
1020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * handlePollStateResult to store CREG roaming result.
1030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
1040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mGsmRoaming = false;
1050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
1070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Data roaming status solely based on TS 27.007 10.1.19 CGREG. Only used by
1080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * handlePollStateResult to store CGREG roaming result.
1090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
1100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mDataRoaming = false;
1110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
1130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Mark when service state is in emergency call only mode
1140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
1150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mEmergencyOnly = false;
1160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
1180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Sometimes we get the NITZ time before we know what country we
1190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * are in. Keep the time zone information from the NITZ string so
1200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * we can fix the time zone once know the country.
1210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
1220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mNeedFixZoneAfterNitz = false;
1230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int mZoneOffset;
1240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mZoneDst;
1250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private long mZoneTime;
1260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mGotCountryCode = false;
1270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private ContentResolver cr;
1280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Boolean is true is setTimeFromNITZString was called */
1300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mNitzUpdatedTime = false;
1310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    String mSavedTimeZone;
1330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    long mSavedTime;
1340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    long mSavedAtTime;
1350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Started the recheck process after finding gprs should registered but not. */
1370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mStartedGprsRegCheck = false;
1380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Already sent the event-log for no gprs register. */
1400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean mReportedGprsNoReg = false;
1410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
1430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * The Notification object given to the NotificationManager.
1440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
1450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private Notification mNotification;
1460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Wake lock used while setting time of day. */
1480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private PowerManager.WakeLock mWakeLock;
1490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private static final String WAKELOCK_TAG = "ServiceStateTracker";
1500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Keep track of SPN display rules, so we only broadcast intent if something changes. */
1520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private String curSpn = null;
1530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private String curPlmn = null;
15460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang    private boolean curShowPlmn = false;
15560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang    private boolean curShowSpn = false;
15660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
1570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** waiting period before recheck gprs and voice registration. */
1590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int DEFAULT_GPRS_CHECK_PERIOD_MILLIS = 60 * 1000;
1600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Notification type. */
1620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int PS_ENABLED = 1001;            // Access Control blocks data service
1630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int PS_DISABLED = 1002;           // Access Control enables data service
1640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int CS_ENABLED = 1003;            // Access Control blocks all voice/sms service
1650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int CS_DISABLED = 1004;           // Access Control enables all voice/sms service
1660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int CS_NORMAL_ENABLED = 1005;     // Access Control blocks normal voice/sms service
1670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int CS_EMERGENCY_ENABLED = 1006;  // Access Control blocks emergency call service
1680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** Notification id. */
1700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int PS_NOTIFICATION = 888;  // Id to update and cancel PS restricted
1710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    static final int CS_NOTIFICATION = 999;  // Id to update and cancel CS restricted
1720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private BroadcastReceiver mIntentReceiver = new BroadcastReceiver() {
1740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        @Override
1750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        public void onReceive(Context context, Intent intent) {
1760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (intent.getAction().equals(Intent.ACTION_LOCALE_CHANGED)) {
1770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // update emergency string whenever locale changed
1780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                updateSpnDisplay();
1790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
1800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
1810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    };
1820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private ContentObserver mAutoTimeObserver = new ContentObserver(new Handler()) {
1840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        @Override
1850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        public void onChange(boolean selfChange) {
1860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            Log.i("GsmServiceStateTracker", "Auto time state changed");
1870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            revertToNitzTime();
1880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
1890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    };
1900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private ContentObserver mAutoTimeZoneObserver = new ContentObserver(new Handler()) {
1920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        @Override
1930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        public void onChange(boolean selfChange) {
1940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            Log.i("GsmServiceStateTracker", "Auto time zone state changed");
1950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            revertToNitzTimeZone();
1960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
1970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    };
1980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public GsmServiceStateTracker(GSMPhone phone) {
200049ab0421f32e6effc5d1277b69bd382cebadb18Wink Saville        super(phone, phone.mCM, new CellInfoGsm());
2010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        this.phone = phone;
2030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cellLoc = new GsmCellLocation();
2040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        newCellLoc = new GsmCellLocation();
2050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        PowerManager powerManager =
2070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                (PowerManager)phone.getContext().getSystemService(Context.POWER_SERVICE);
2080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mWakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, WAKELOCK_TAG);
2090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.registerForAvailable(this, EVENT_RADIO_AVAILABLE, null);
2110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.registerForRadioStateChanged(this, EVENT_RADIO_STATE_CHANGED, null);
2120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.registerForVoiceNetworkStateChanged(this, EVENT_NETWORK_STATE_CHANGED, null);
2140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.setOnNITZTime(this, EVENT_NITZ_TIME, null);
2150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.setOnRestrictedStateChanged(this, EVENT_RESTRICTED_STATE_CHANGED, null);
2160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // system setting property AIRPLANE_MODE_ON is set in Settings.
2180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int airplaneMode = Settings.System.getInt(
2190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                phone.getContext().getContentResolver(),
2200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                Settings.System.AIRPLANE_MODE_ON, 0);
2210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mDesiredPowerState = ! (airplaneMode > 0);
2220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cr = phone.getContext().getContentResolver();
2240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cr.registerContentObserver(
2250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                Settings.System.getUriFor(Settings.System.AUTO_TIME), true,
2260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mAutoTimeObserver);
2270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cr.registerContentObserver(
2280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                Settings.System.getUriFor(Settings.System.AUTO_TIME_ZONE), true,
2290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mAutoTimeZoneObserver);
2300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        setSignalStrengthDefaultValues();
2320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Monitor locale change
2340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        IntentFilter filter = new IntentFilter();
2350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        filter.addAction(Intent.ACTION_LOCALE_CHANGED);
2360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        phone.getContext().registerReceiver(mIntentReceiver, filter);
2370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Gsm doesn't support OTASP so its not needed
2390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        phone.notifyOtaspChanged(OTASP_NOT_NEEDED);
2400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
2410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
242ef1d4bff9bbf7d967dbcace73f08910e14e367d0Wink Saville    @Override
2430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public void dispose() {
244e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka        checkCorrectThread();
2450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Unregister for all events.
2460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.unregisterForAvailable(this);
2470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.unregisterForRadioStateChanged(this);
2480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.unregisterForVoiceNetworkStateChanged(this);
249e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        if (mUiccApplcation != null) {mUiccApplcation.unregisterForReady(this);}
250e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka        if (mIccRecords != null) {mIccRecords.unregisterForRecordsLoaded(this);}
2510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.unSetOnRestrictedStateChanged(this);
2520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.unSetOnNITZTime(this);
2530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cr.unregisterContentObserver(this.mAutoTimeObserver);
2540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cr.unregisterContentObserver(this.mAutoTimeZoneObserver);
255a5fc984c8b0696c187e14bfa75962b6e46c40d02Alex Yakavenka        phone.getContext().unregisterReceiver(mIntentReceiver);
256ef1d4bff9bbf7d967dbcace73f08910e14e367d0Wink Saville        super.dispose();
2570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
2580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void finalize() {
2600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if(DBG) log("finalize");
2610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
2620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    @Override
2640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected Phone getPhone() {
2650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return phone;
2660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
2670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public void handleMessage (Message msg) {
2690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        AsyncResult ar;
2700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int[] ints;
2710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String[] strings;
2720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Message message;
2730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (!phone.mIsTheCurrentActivePhone) {
2750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            Log.e(LOG_TAG, "Received message " + msg +
2760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    "[" + msg.what + "] while being destroyed. Ignoring.");
2770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return;
2780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
2790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        switch (msg.what) {
2800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_RADIO_AVAILABLE:
2810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                //this is unnecessary
2820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                //setPowerStateToDesired();
2830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
2840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_SIM_READY:
2860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Set the network type, in case the radio does not restore it.
2870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.setCurrentPreferredNetworkType();
2880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                boolean skipRestoringSelection = phone.getContext().getResources().getBoolean(
2900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        com.android.internal.R.bool.skip_restoring_network_selection);
2910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
2920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!skipRestoringSelection) {
2930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // restore the previous network selection.
2940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    phone.restoreSavedNetworkSelection(null);
2950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
2960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollState();
2970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Signal strength polling stops when radio is off
2980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                queueNextSignalStrengthPoll();
2990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_RADIO_STATE_CHANGED:
3020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // This will do nothing in the radio not
3030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // available case
3040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setPowerStateToDesired();
3050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollState();
3060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_NETWORK_STATE_CHANGED:
3090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollState();
3100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_GET_SIGNAL_STRENGTH:
3130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // This callback is called when signal strength is polled
3140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // all by itself
3150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!(cm.getRadioState().isOn())) {
3170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // Polling will continue when radio turns back on
3180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    return;
3190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
3200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
321e0e2ceb1ae025e6dd2adda75c32dba93c6dfeea4Wink Saville                onSignalStrengthResult(ar, true);
3220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                queueNextSignalStrengthPoll();
3230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_GET_LOC_DONE:
3270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
3280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (ar.exception == null) {
3300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    String states[] = (String[])ar.result;
3310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int lac = -1;
3320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int cid = -1;
3330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (states.length >= 3) {
3340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        try {
3350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states[1] != null && states[1].length() > 0) {
3360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                lac = Integer.parseInt(states[1], 16);
3370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
3380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states[2] != null && states[2].length() > 0) {
3390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                cid = Integer.parseInt(states[2], 16);
3400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
3410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        } catch (NumberFormatException ex) {
3420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            Log.w(LOG_TAG, "error parsing location: " + ex);
3430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
3440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
3450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    cellLoc.setLacAndCid(lac, cid);
3460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    phone.notifyLocationChanged();
3470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
3480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Release any temporary cell lock, which could have been
3500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // acquired to allow a single-shot location update.
3510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                disableSingleLocationUpdate();
3520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_POLL_STATE_REGISTRATION:
3550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_POLL_STATE_GPRS:
3560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_POLL_STATE_OPERATOR:
3570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_POLL_STATE_NETWORK_SELECTION_MODE:
3580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
3590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                handlePollStateResult(msg.what, ar);
3610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_POLL_SIGNAL_STRENGTH:
3640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Just poll signal strength...not part of pollState()
3650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.getSignalStrength(obtainMessage(EVENT_GET_SIGNAL_STRENGTH));
3670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_NITZ_TIME:
3700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
3710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                String nitzString = (String)((Object[])ar.result)[0];
3730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                long nitzReceiveTime = ((Long)((Object[])ar.result)[1]).longValue();
3740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setTimeFromNITZString(nitzString, nitzReceiveTime);
3760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_SIGNAL_STRENGTH_UPDATE:
3790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // This is a notification from
3800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // CommandsInterface.setOnSignalStrengthUpdate
3810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
3830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // The radio is telling us about signal strength changes
3850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // we don't have to ask it
3860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                dontPollSignalStrength = true;
3870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
388e0e2ceb1ae025e6dd2adda75c32dba93c6dfeea4Wink Saville                onSignalStrengthResult(ar, true);
3890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_SIM_RECORDS_LOADED:
3920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                updateSpnDisplay();
3930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
3940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_LOCATION_UPDATES_ENABLED:
3960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
3970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
3980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (ar.exception == null) {
3990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    cm.getVoiceRegistrationState(obtainMessage(EVENT_GET_LOC_DONE, null));
4000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
4010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_SET_PREFERRED_NETWORK_TYPE:
4040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
4050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Don't care the result, only use for dereg network (COPS=2)
4060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                message = obtainMessage(EVENT_RESET_PREFERRED_NETWORK_TYPE, ar.userObj);
4070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.setPreferredNetworkType(mPreferredNetworkType, message);
4080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_RESET_PREFERRED_NETWORK_TYPE:
4110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
4120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (ar.userObj != null) {
4130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    AsyncResult.forMessage(((Message) ar.userObj)).exception
4140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            = ar.exception;
4150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ((Message) ar.userObj).sendToTarget();
4160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
4170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_GET_PREFERRED_NETWORK_TYPE:
4200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
4210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (ar.exception == null) {
4230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mPreferredNetworkType = ((int[])ar.result)[0];
4240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else {
4250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mPreferredNetworkType = RILConstants.NETWORK_MODE_GLOBAL;
4260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
4270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                message = obtainMessage(EVENT_SET_PREFERRED_NETWORK_TYPE, ar.userObj);
4290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                int toggledNetworkType = RILConstants.NETWORK_MODE_GLOBAL;
4300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.setPreferredNetworkType(toggledNetworkType, message);
4320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_CHECK_REPORT_GPRS:
4350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (ss != null && !isGprsConsistent(gprsState, ss.getState())) {
4360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // Can't register data service while voice service is ok
4380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // i.e. CREG is ok while CGREG is not
4390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // possible a network or baseband side error
4400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    GsmCellLocation loc = ((GsmCellLocation)phone.getCellLocation());
4410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    EventLog.writeEvent(EventLogTags.DATA_NETWORK_REGISTRATION_FAIL,
4420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            ss.getOperatorNumeric(), loc != null ? loc.getCid() : -1);
4430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mReportedGprsNoReg = true;
4440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
4450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mStartedGprsRegCheck = false;
4460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case EVENT_RESTRICTED_STATE_CHANGED:
4490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // This is a notification from
4500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // CommandsInterface.setOnRestrictedStateChanged
4510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (DBG) log("EVENT_RESTRICTED_STATE_CHANGED");
4530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ar = (AsyncResult) msg.obj;
4550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                onRestrictedStateChanged(ar);
4570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
4580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            default:
4600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                super.handleMessage(msg);
4610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
4620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
4630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
4640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void setPowerStateToDesired() {
4660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // If we want it on and it's off, turn it on
4670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (mDesiredPowerState
4680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            && cm.getRadioState() == CommandsInterface.RadioState.RADIO_OFF) {
4690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            cm.setRadioPower(true, null);
4700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } else if (!mDesiredPowerState && cm.getRadioState().isOn()) {
4710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // If it's on and available and we want it off gracefully
4720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            DataConnectionTracker dcTracker = phone.mDataConnectionTracker;
4730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            powerOffRadioSafely(dcTracker);
4740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } // Otherwise, we're in the desired state
4750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
4760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    @Override
4780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void hangupAndPowerOff() {
4790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // hang up all active voice calls
4800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (phone.isInCall()) {
4810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.mCT.ringingCall.hangupIfAlive();
4820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.mCT.backgroundCall.hangupIfAlive();
4830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.mCT.foregroundCall.hangupIfAlive();
4840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
4850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
4860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cm.setRadioPower(false, null);
4870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
4880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
489f7a8133113daddcc48a41e451193afd3fcb35e16Wink Saville    @Override
4900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void updateSpnDisplay() {
49160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // The values of plmn/showPlmn change in different scenarios.
49260e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // 1) No service but emergency call allowed -> expected
49360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    to show "Emergency call only"
49460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SHOW_PLMN = true
49560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_PLMN = "Emergency call only"
49660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
49760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // 2) No service at all --> expected to show "No service"
49860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SHOW_PLMN = true
49960e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_PLMN = "No service"
50060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
50160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // 3) Normal operation in either home or roaming service
50260e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SHOW_PLMN = depending on IccRecords rule
50360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_PLMN = plmn
50460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
50560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // 4) No service due to power off, aka airplane mode
50660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SHOW_PLMN = false
50760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_PLMN = null
50860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
509f7a8133113daddcc48a41e451193afd3fcb35e16Wink Saville        IccRecords iccRecords = mIccRecords;
51060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        String plmn = null;
51160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        boolean showPlmn = false;
512f7a8133113daddcc48a41e451193afd3fcb35e16Wink Saville        int rule = (iccRecords != null) ? iccRecords.getDisplayRule(ss.getOperatorNumeric()) : 0;
51360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        if (ss.getState() == ServiceState.STATE_OUT_OF_SERVICE
51460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                || ss.getState() == ServiceState.STATE_EMERGENCY_ONLY) {
51560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            showPlmn = true;
51660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            if (mEmergencyOnly) {
51760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                // No service but emergency call allowed
51860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                plmn = Resources.getSystem().
51960e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        getText(com.android.internal.R.string.emergency_calls_only).toString();
52060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            } else {
52160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                // No service at all
52260e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                plmn = Resources.getSystem().
52360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        getText(com.android.internal.R.string.lockscreen_carrier_default).toString();
52460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            }
52560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            if (DBG) log("updateSpnDisplay: radio is on but out " +
52660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                    "of service, set plmn='" + plmn + "'");
52760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        } else if (ss.getState() == ServiceState.STATE_IN_SERVICE) {
52860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            // In either home or roaming service
52960e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            plmn = ss.getOperatorAlphaLong();
53060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            showPlmn = !TextUtils.isEmpty(plmn) &&
53160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                    ((rule & SIMRecords.SPN_RULE_SHOW_PLMN)
53260e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                            == SIMRecords.SPN_RULE_SHOW_PLMN);
53360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        } else {
53460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            // Power off state, such as airplane mode
53560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang            if (DBG) log("updateSpnDisplay: radio is off w/ showPlmn="
53660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                    + showPlmn + " plmn=" + plmn);
5370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
5380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
53960e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // The value of spn/showSpn are same in different scenarios.
54060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SHOW_SPN = depending on IccRecords rule
54160e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        //    EXTRA_SPN = spn
542f7a8133113daddcc48a41e451193afd3fcb35e16Wink Saville        String spn = (iccRecords != null) ? iccRecords.getServiceProviderName() : "";
54360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        boolean showSpn = !TextUtils.isEmpty(spn)
54460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                && ((rule & SIMRecords.SPN_RULE_SHOW_SPN)
54560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        == SIMRecords.SPN_RULE_SHOW_SPN);
54660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang
54760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        // Update SPN_STRINGS_UPDATED_ACTION IFF any value changes
54860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        if (showPlmn != curShowPlmn
54960e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                || showSpn != curShowSpn
5500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                || !TextUtils.equals(spn, curSpn)
5510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                || !TextUtils.equals(plmn, curPlmn)) {
5520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (DBG) {
55360e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                log(String.format("updateSpnDisplay: changed" +
55460e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        " sending intent rule=" + rule +
55560e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        " showPlmn='%b' plmn='%s' showSpn='%b' spn='%s'",
55660e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang                        showPlmn, plmn, showSpn, spn));
5570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
5580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            Intent intent = new Intent(TelephonyIntents.SPN_STRINGS_UPDATED_ACTION);
5590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING);
5600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            intent.putExtra(TelephonyIntents.EXTRA_SHOW_SPN, showSpn);
5610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            intent.putExtra(TelephonyIntents.EXTRA_SPN, spn);
5620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            intent.putExtra(TelephonyIntents.EXTRA_SHOW_PLMN, showPlmn);
5630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            intent.putExtra(TelephonyIntents.EXTRA_PLMN, plmn);
5647eff443d1f090abdbbd93eef9f265c74890920bcDianne Hackborn            phone.getContext().sendStickyBroadcastAsUser(intent, UserHandle.ALL);
5650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
5660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
56760e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        curShowSpn = showSpn;
56860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        curShowPlmn = showPlmn;
5690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        curSpn = spn;
5700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        curPlmn = plmn;
5710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
5720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
5740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Handle the result of one of the pollState()-related requests
5750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
5760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void handlePollStateResult (int what, AsyncResult ar) {
5770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int ints[];
5780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String states[];
5790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Ignore stale requests from last poll
5810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (ar.userObj != pollingContext) return;
5820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (ar.exception != null) {
5840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            CommandException.Error err=null;
5850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (ar.exception instanceof CommandException) {
5870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                err = ((CommandException)(ar.exception)).getCommandError();
5880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
5890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (err == CommandException.Error.RADIO_NOT_AVAILABLE) {
5910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Radio has crashed or turned off
5920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cancelPollState();
5930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return;
5940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
5950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
5960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (!cm.getRadioState().isOn()) {
5970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Radio has crashed or turned off
5980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cancelPollState();
5990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return;
6000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
6010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (err != CommandException.Error.OP_NOT_ALLOWED_BEFORE_REG_NW) {
6030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                loge("RIL implementation has returned an error where it must succeed" +
6040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        ar.exception);
6050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
6060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } else try {
6070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            switch (what) {
6080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                case EVENT_POLL_STATE_REGISTRATION:
6090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    states = (String[])ar.result;
6100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int lac = -1;
6110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int cid = -1;
6120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int regState = -1;
6130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int reasonRegStateDenied = -1;
6140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int psc = -1;
6150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (states.length > 0) {
6160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        try {
6170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            regState = Integer.parseInt(states[0]);
6180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states.length >= 3) {
6190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                if (states[1] != null && states[1].length() > 0) {
6200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                    lac = Integer.parseInt(states[1], 16);
6210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                }
6220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                if (states[2] != null && states[2].length() > 0) {
6230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                    cid = Integer.parseInt(states[2], 16);
6240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                }
6250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
6260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states.length > 14) {
6270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                if (states[14] != null && states[14].length() > 0) {
6280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                    psc = Integer.parseInt(states[14], 16);
6290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                }
6300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
6310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        } catch (NumberFormatException ex) {
6320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            loge("error parsing RegistrationState: " + ex);
6330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
6340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
6350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mGsmRoaming = regCodeIsRoaming(regState);
6370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newSS.setState (regCodeToServiceState(regState));
6380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (regState == 10 || regState == 12 || regState == 13 || regState == 14) {
6400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        mEmergencyOnly = true;
6410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else {
6420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        mEmergencyOnly = false;
6430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
6440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // LAC and CID are -1 if not avail
6460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newCellLoc.setLacAndCid(lac, cid);
6470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newCellLoc.setPsc(psc);
6480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
6490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                case EVENT_POLL_STATE_GPRS:
6510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    states = (String[])ar.result;
6520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    int type = 0;
6540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    regState = -1;
6550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mNewReasonDataDenied = -1;
6560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mNewMaxDataCalls = 1;
6570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (states.length > 0) {
6580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        try {
6590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            regState = Integer.parseInt(states[0]);
6600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            // states[3] (if present) is the current radio technology
6620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states.length >= 4 && states[3] != null) {
6630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                type = Integer.parseInt(states[3]);
6640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
6650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if ((states.length >= 5 ) && (regState == 3)) {
6660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                mNewReasonDataDenied = Integer.parseInt(states[4]);
6670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
6680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (states.length >= 6) {
6690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                mNewMaxDataCalls = Integer.parseInt(states[5]);
6700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
6710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        } catch (NumberFormatException ex) {
6720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            loge("error parsing GprsRegistrationState: " + ex);
6730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
6740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
6750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newGPRSState = regCodeToServiceState(regState);
6760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mDataRoaming = regCodeIsRoaming(regState);
6770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mNewRilRadioTechnology = type;
6780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newSS.setRadioTechnology(type);
6790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
6800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                case EVENT_POLL_STATE_OPERATOR:
6820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    String opNames[] = (String[])ar.result;
6830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (opNames != null && opNames.length >= 3) {
6850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                         newSS.setOperatorName (opNames[0], opNames[1], opNames[2]);
6860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
6870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
6880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                case EVENT_POLL_STATE_NETWORK_SELECTION_MODE:
6900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ints = (int[])ar.result;
6910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    newSS.setIsManualSelection(ints[0] == 1);
6920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
6930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
6940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
6950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } catch (RuntimeException ex) {
6960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            loge("Exception while polling service state. Probably malformed RIL response." + ex);
6970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
6980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
699708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma        final boolean voice_capable = phone.getContext().getResources().getBoolean(
700708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma                com.android.internal.R.bool.config_voice_capable);
701708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma
702708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma        if (!voice_capable && newGPRSState == ServiceState.STATE_IN_SERVICE) {
703708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma            newSS.setState (newGPRSState);
704708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma        }
705708cb897813b5239e1d732d08ee2d04f577d09f1Junichi Monma
7060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pollingContext[0]--;
7070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (pollingContext[0] == 0) {
7090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            /**
7100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  Since the roaming states of gsm service (from +CREG) and
7110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  data service (from +CGREG) could be different, the new SS
7120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  is set roaming while either one is roaming.
7130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *
7140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  There is an exception for the above rule. The new SS is not set
7150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  as roaming while gsm service reports roaming but indeed it is
7160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             *  not roaming between operators.
7170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             */
7180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            boolean roaming = (mGsmRoaming || mDataRoaming);
7190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (mGsmRoaming && !isRoamingBetweenOperators(mGsmRoaming, newSS)) {
7200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                roaming = false;
7210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
7220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            newSS.setRoaming(roaming);
7230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            newSS.setEmergencyOnly(mEmergencyOnly);
7240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            pollStateDone();
7250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
7260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
7270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
728c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void setSignalStrengthDefaultValues() {
7295b81adc82a53b3064f4baa3acfeabef31586588aUma Maheswari Ramalingam        mSignalStrength = new SignalStrength(true);
7300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
7310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
7330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * A complete "service state" from our perspective is
7340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * composed of a handful of separate requests to the radio.
7350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
7360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * We make all of these requests at once, but then abandon them
7370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * and start over again if the radio notifies us that some
7380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * event has changed
7390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
7400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void pollState() {
7410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pollingContext = new int[1];
7420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pollingContext[0] = 0;
7430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        switch (cm.getRadioState()) {
7450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case RADIO_UNAVAILABLE:
7460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newSS.setStateOutOfService();
7470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newCellLoc.setStateInvalid();
7480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setSignalStrengthDefaultValues();
7490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mGotCountryCode = false;
7500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNitzUpdatedTime = false;
7510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollStateDone();
7520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
7530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case RADIO_OFF:
7550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newSS.setStateOff();
7560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newCellLoc.setStateInvalid();
7570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setSignalStrengthDefaultValues();
7580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mGotCountryCode = false;
7590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNitzUpdatedTime = false;
7600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollStateDone();
7610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
7620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            default:
7640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // Issue all poll-related commands at once
7650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // then count down the responses, which
7660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // are allowed to arrive out-of-order
7670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollingContext[0]++;
7690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.getOperator(
7700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    obtainMessage(
7710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        EVENT_POLL_STATE_OPERATOR, pollingContext));
7720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollingContext[0]++;
7740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.getDataRegistrationState(
7750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    obtainMessage(
7760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        EVENT_POLL_STATE_GPRS, pollingContext));
7770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollingContext[0]++;
7790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.getVoiceRegistrationState(
7800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    obtainMessage(
7810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        EVENT_POLL_STATE_REGISTRATION, pollingContext));
7820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                pollingContext[0]++;
7840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                cm.getNetworkSelectionMode(
7850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    obtainMessage(
7860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        EVENT_POLL_STATE_NETWORK_SELECTION_MODE, pollingContext));
7870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
7880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
7890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
7900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
7910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void pollStateDone() {
7920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) {
7930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            log("Poll ServiceState done: " +
7940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " oldSS=[" + ss + "] newSS=[" + newSS +
7950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                "] oldGprs=" + gprsState + " newData=" + newGPRSState +
7960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " oldMaxDataCalls=" + mMaxDataCalls +
7970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " mNewMaxDataCalls=" + mNewMaxDataCalls +
7980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " oldReasonDataDenied=" + mReasonDataDenied +
7990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " mNewReasonDataDenied=" + mNewReasonDataDenied +
8000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " oldType=" + ServiceState.rilRadioTechnologyToString(mRilRadioTechnology) +
8010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                " newType=" + ServiceState.rilRadioTechnologyToString(mNewRilRadioTechnology));
8020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
8030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasRegistered =
8050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            ss.getState() != ServiceState.STATE_IN_SERVICE
8060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            && newSS.getState() == ServiceState.STATE_IN_SERVICE;
8070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasDeregistered =
8090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            ss.getState() == ServiceState.STATE_IN_SERVICE
8100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            && newSS.getState() != ServiceState.STATE_IN_SERVICE;
8110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasGprsAttached =
8130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                gprsState != ServiceState.STATE_IN_SERVICE
8140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                && newGPRSState == ServiceState.STATE_IN_SERVICE;
8150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasGprsDetached =
8170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                gprsState == ServiceState.STATE_IN_SERVICE
8180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                && newGPRSState != ServiceState.STATE_IN_SERVICE;
8190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasRadioTechnologyChanged = mRilRadioTechnology != mNewRilRadioTechnology;
8210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasChanged = !newSS.equals(ss);
8230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasRoamingOn = !ss.getRoaming() && newSS.getRoaming();
8250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasRoamingOff = ss.getRoaming() && !newSS.getRoaming();
8270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean hasLocationChanged = !newCellLoc.equals(cellLoc);
8290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Add an event log when connection state changes
8310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (ss.getState() != newSS.getState() || gprsState != newGPRSState) {
8320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            EventLog.writeEvent(EventLogTags.GSM_SERVICE_STATE_CHANGE,
8330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ss.getState(), gprsState, newSS.getState(), newGPRSState);
8340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
8350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        ServiceState tss;
8370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        tss = ss;
8380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        ss = newSS;
8390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        newSS = tss;
8400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // clean slate for next time
8410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        newSS.setStateOutOfService();
8420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        GsmCellLocation tcl = cellLoc;
8440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        cellLoc = newCellLoc;
8450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        newCellLoc = tcl;
8460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // Add an event log when network type switched
8480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // TODO: we may add filtering to reduce the event logged,
8490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // i.e. check preferred network setting, only switch to 2G, etc
8500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRadioTechnologyChanged) {
8510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int cid = -1;
8520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            GsmCellLocation loc = ((GsmCellLocation)phone.getCellLocation());
8530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (loc != null) cid = loc.getCid();
8540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            EventLog.writeEvent(EventLogTags.GSM_RAT_SWITCHED, cid, mRilRadioTechnology,
8550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mNewRilRadioTechnology);
8560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (DBG) {
8570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                log("RAT switched " + ServiceState.rilRadioTechnologyToString(mRilRadioTechnology) +
8580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        " -> " + ServiceState.rilRadioTechnologyToString(mNewRilRadioTechnology) +
8590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        " at cell " + cid);
8600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
8610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
8620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        gprsState = newGPRSState;
8640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mReasonDataDenied = mNewReasonDataDenied;
8650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mMaxDataCalls = mNewMaxDataCalls;
8660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mRilRadioTechnology = mNewRilRadioTechnology;
8670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // this new state has been applied - forget it until we get a new new state
8680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNewRilRadioTechnology = 0;
8690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        newSS.setStateOutOfService(); // clean slate for next time
8720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRadioTechnologyChanged) {
8740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.setSystemProperty(TelephonyProperties.PROPERTY_DATA_NETWORK_TYPE,
8750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ServiceState.rilRadioTechnologyToString(mRilRadioTechnology));
8760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
8770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRegistered) {
8790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mNetworkAttachedRegistrants.notifyRegistrants();
8800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (DBG) {
8820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                log("pollStateDone: registering current mNitzUpdatedTime=" +
8830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        mNitzUpdatedTime + " changing to false");
8840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
8850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mNitzUpdatedTime = false;
8860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
8870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasChanged) {
8890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            String operatorNumeric;
8900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            updateSpnDisplay();
8920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_ALPHA,
8940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ss.getOperatorAlphaLong());
8950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
8960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            String prevOperatorNumeric =
8970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    SystemProperties.get(TelephonyProperties.PROPERTY_OPERATOR_NUMERIC, "");
8980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            operatorNumeric = ss.getOperatorNumeric();
8990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_NUMERIC, operatorNumeric);
9000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (operatorNumeric == null) {
9020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (DBG) log("operatorNumeric is null");
9030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_ISO_COUNTRY, "");
9040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mGotCountryCode = false;
9050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNitzUpdatedTime = false;
9060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } else {
9070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                String iso = "";
9087c491bb3d140e2579c2c01edca94305701664db5Rekha Kumar                String mcc = "";
9090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                try{
9107c491bb3d140e2579c2c01edca94305701664db5Rekha Kumar                    mcc = operatorNumeric.substring(0, 3);
9110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    iso = MccTable.countryCodeForMcc(Integer.parseInt(mcc));
9120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } catch ( NumberFormatException ex){
9130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    loge("pollStateDone: countryCodeForMcc error" + ex);
9140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } catch ( StringIndexOutOfBoundsException ex) {
9150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    loge("pollStateDone: countryCodeForMcc error" + ex);
9160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
9170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_ISO_COUNTRY, iso);
9190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mGotCountryCode = true;
9200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                TimeZone zone = null;
9220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!mNitzUpdatedTime && !mcc.equals("000") && !TextUtils.isEmpty(iso) &&
9240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        getAutoTimeZone()) {
9250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // Test both paths if ignore nitz is true
9270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    boolean testOneUniqueOffsetPath = SystemProperties.getBoolean(
9280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                TelephonyProperties.PROPERTY_IGNORE_NITZ, false) &&
9290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                    ((SystemClock.uptimeMillis() & 1) == 0);
9300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ArrayList<TimeZone> uniqueZones = TimeUtils.getTimeZonesWithUniqueOffsets(iso);
9320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if ((uniqueZones.size() == 1) || testOneUniqueOffsetPath) {
9330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = uniqueZones.get(0);
9340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) {
9350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                           log("pollStateDone: no nitz but one TZ for iso-cc=" + iso +
9360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                   " with zone.getID=" + zone.getID() +
9370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                   " testOneUniqueOffsetPath=" + testOneUniqueOffsetPath);
9380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
9390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        setAndBroadcastNetworkSetTimeZone(zone.getID());
9400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else {
9410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) {
9420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            log("pollStateDone: there are " + uniqueZones.size() +
9430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                " unique offsets for iso-cc='" + iso +
9440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                " testOneUniqueOffsetPath=" + testOneUniqueOffsetPath +
9450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                "', do nothing");
9460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
9470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
9480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
9490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (shouldFixTimeZoneNow(phone, operatorNumeric, prevOperatorNumeric,
9510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        mNeedFixZoneAfterNitz)) {
9520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // If the offset is (0, false) and the timezone property
9530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // is set, use the timezone property rather than
9540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // GMT.
9550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    String zoneName = SystemProperties.get(TIMEZONE_PROPERTY);
9560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (DBG) {
9570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        log("pollStateDone: fix time zone zoneName='" + zoneName +
9580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            "' mZoneOffset=" + mZoneOffset + " mZoneDst=" + mZoneDst +
9590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            " iso-cc='" + iso +
9600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            "' iso-cc-idx=" + Arrays.binarySearch(GMT_COUNTRY_CODES, iso));
9610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
9620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
9630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // "(mZoneOffset == 0) && (mZoneDst == false) &&
9640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    //  (Arrays.binarySearch(GMT_COUNTRY_CODES, iso) < 0)"
9650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // means that we received a NITZ string telling
9660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // it is in GMT+0 w/ DST time zone
9670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // BUT iso tells is NOT, e.g, a wrong NITZ reporting
9680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // local time w/ 0 offset.
9690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if ((mZoneOffset == 0) && (mZoneDst == false) &&
9700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        (zoneName != null) && (zoneName.length() > 0) &&
9710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        (Arrays.binarySearch(GMT_COUNTRY_CODES, iso) < 0)) {
9720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = TimeZone.getDefault();
9730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (mNeedFixZoneAfterNitz) {
9740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            // For wrong NITZ reporting local time w/ 0 offset,
9750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            // need adjust time to reflect default timezone setting
9760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            long ctm = System.currentTimeMillis();
9770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            long tzOffset = zone.getOffset(ctm);
9780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (DBG) {
9790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                log("pollStateDone: tzOffset=" + tzOffset + " ltod=" +
9800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                        TimeUtils.logTimeOfDay(ctm));
9810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
9820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            if (getAutoTime()) {
9830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                long adj = ctm - tzOffset;
9840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                if (DBG) log("pollStateDone: adj ltod=" +
9850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                        TimeUtils.logTimeOfDay(adj));
9860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                setAndBroadcastNetworkSetTime(adj);
9870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            } else {
9880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                // Adjust the saved NITZ time to account for tzOffset.
9890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                mSavedTime = mSavedTime - tzOffset;
9900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            }
9910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
9920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) log("pollStateDone: using default TimeZone");
9930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else if (iso.equals("")){
9940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // Country code not found.  This is likely a test network.
9950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // Get a TimeZone based only on the NITZ parameters (best guess).
9960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = getNitzTimeZone(mZoneOffset, mZoneDst, mZoneTime);
9970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) log("pollStateDone: using NITZ TimeZone");
9980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else {
9990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = TimeUtils.getTimeZone(mZoneOffset, mZoneDst, mZoneTime, iso);
10000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) log("pollStateDone: using getTimeZone(off, dst, time, iso)");
10010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
10020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mNeedFixZoneAfterNitz = false;
10040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (zone != null) {
10060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        log("pollStateDone: zone != null zone.getID=" + zone.getID());
10070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (getAutoTimeZone()) {
10080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            setAndBroadcastNetworkSetTimeZone(zone.getID());
10090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
10100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        saveNitzTimeZone(zone.getID());
10110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else {
10120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        log("pollStateDone: zone == null");
10130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
10140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
10150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
10160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_ISROAMING,
10180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                ss.getRoaming() ? "true" : "false");
10190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.notifyServiceStateChanged(ss);
10210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasGprsAttached) {
10240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mAttachedRegistrants.notifyRegistrants();
10250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasGprsDetached) {
10280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mDetachedRegistrants.notifyRegistrants();
10290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRadioTechnologyChanged) {
10320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.notifyDataConnection(Phone.REASON_NW_TYPE_CHANGED);
10330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRoamingOn) {
10360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mRoamingOnRegistrants.notifyRegistrants();
10370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasRoamingOff) {
10400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mRoamingOffRegistrants.notifyRegistrants();
10410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (hasLocationChanged) {
10440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            phone.notifyLocationChanged();
10450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (! isGprsConsistent(gprsState, ss.getState())) {
10480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (!mStartedGprsRegCheck && !mReportedGprsNoReg) {
10490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mStartedGprsRegCheck = true;
10500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
1051b840987a39e7149c1364739696977089cd53814dWink Saville                int check_period = Settings.Global.getInt(
10520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        phone.getContext().getContentResolver(),
1053b840987a39e7149c1364739696977089cd53814dWink Saville                        Settings.Global.GPRS_REGISTER_CHECK_PERIOD_MS,
10540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        DEFAULT_GPRS_CHECK_PERIOD_MILLIS);
10550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                sendMessageDelayed(obtainMessage(EVENT_CHECK_REPORT_GPRS),
10560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        check_period);
10570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
10580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } else {
10590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mReportedGprsNoReg = false;
10600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
1061ef1d4bff9bbf7d967dbcace73f08910e14e367d0Wink Saville        // TODO: Add GsmCellIdenity updating, see CdmaLteServiceStateTracker.
10620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
10630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
10650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Check if GPRS got registered while voice is registered.
10660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
10670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param gprsState for GPRS registration state, i.e. CGREG in GSM
10680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param serviceState for voice registration state, i.e. CREG in GSM
10690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @return false if device only register to voice but not gprs
10700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
10710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean isGprsConsistent(int gprsState, int serviceState) {
10720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return !((serviceState == ServiceState.STATE_IN_SERVICE) &&
10730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                (gprsState != ServiceState.STATE_IN_SERVICE));
10740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
10750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
10770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Returns a TimeZone object based only on parameters from the NITZ string.
10780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
10790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private TimeZone getNitzTimeZone(int offset, boolean dst, long when) {
10800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        TimeZone guess = findTimeZone(offset, dst, when);
10810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (guess == null) {
10820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // Couldn't find a proper timezone.  Perhaps the DST data is wrong.
10830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            guess = findTimeZone(offset, !dst, when);
10840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("getNitzTimeZone returning " + (guess == null ? guess : guess.getID()));
10860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return guess;
10870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
10880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
10890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private TimeZone findTimeZone(int offset, boolean dst, long when) {
10900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int rawOffset = offset;
10910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (dst) {
10920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            rawOffset -= 3600000;
10930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
10940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String[] zones = TimeZone.getAvailableIDs(rawOffset);
10950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        TimeZone guess = null;
10960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Date d = new Date(when);
10970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        for (String zone : zones) {
10980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            TimeZone tz = TimeZone.getTimeZone(zone);
10990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (tz.getOffset(when) == offset &&
11000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                tz.inDaylightTime(d) == dst) {
11010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                guess = tz;
11020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                break;
11030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
11040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
11050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return guess;
11070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
11080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void queueNextSignalStrengthPoll() {
11100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (dontPollSignalStrength) {
11110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // The radio is telling us about signal strength changes
11120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // we don't have to ask it
11130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return;
11140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
11150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Message msg;
11170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        msg = obtainMessage();
11190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        msg.what = EVENT_POLL_SIGNAL_STRENGTH;
11200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        long nextTime;
11220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // TODO Don't poll signal strength if screen is off
11240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        sendMessageDelayed(msg, POLL_PERIOD_MILLIS);
11250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
11260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
11280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Set restricted state based on the OnRestrictedStateChanged notification
11290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * If any voice or packet restricted state changes, trigger a UI
11300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * notification and notify registrants when sim is ready.
11310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
11320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param ar an int value of RIL_RESTRICTED_STATE_*
11330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
11340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void onRestrictedStateChanged(AsyncResult ar) {
11350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        RestrictedState newRs = new RestrictedState();
11360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("onRestrictedStateChanged: E rs "+ mRestrictedState);
11380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (ar.exception == null) {
11400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int[] ints = (int[])ar.result;
11410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int state = ints[0];
11420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            newRs.setCsEmergencyRestricted(
11440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ((state & RILConstants.RIL_RESTRICTED_STATE_CS_EMERGENCY) != 0) ||
11450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    ((state & RILConstants.RIL_RESTRICTED_STATE_CS_ALL) != 0) );
11460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            //ignore the normal call and data restricted state before SIM READY
1147e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka            if (mUiccApplcation != null && mUiccApplcation.getState() == AppState.APPSTATE_READY) {
11480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newRs.setCsNormalRestricted(
11490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        ((state & RILConstants.RIL_RESTRICTED_STATE_CS_NORMAL) != 0) ||
11500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        ((state & RILConstants.RIL_RESTRICTED_STATE_CS_ALL) != 0) );
11510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                newRs.setPsRestricted(
11520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        (state & RILConstants.RIL_RESTRICTED_STATE_PS_ALL)!= 0);
11530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
11540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (DBG) log("onRestrictedStateChanged: new rs "+ newRs);
11560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (!mRestrictedState.isPsRestricted() && newRs.isPsRestricted()) {
11580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mPsRestrictEnabledRegistrants.notifyRegistrants();
11590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setNotification(PS_ENABLED);
11600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } else if (mRestrictedState.isPsRestricted() && !newRs.isPsRestricted()) {
11610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mPsRestrictDisabledRegistrants.notifyRegistrants();
11620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                setNotification(PS_DISABLED);
11630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
11640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
11650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            /**
11660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             * There are two kind of cs restriction, normal and emergency. So
11670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             * there are 4 x 4 combinations in current and new restricted states
11680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             * and we only need to notify when state is changed.
11690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             */
11700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (mRestrictedState.isCsRestricted()) {
11710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!newRs.isCsRestricted()) {
11720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove all restriction
11730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_DISABLED);
11740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (!newRs.isCsNormalRestricted()) {
11750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove normal restriction
11760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_EMERGENCY_ENABLED);
11770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (!newRs.isCsEmergencyRestricted()) {
11780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove emergency restriction
11790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_NORMAL_ENABLED);
11800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
11810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } else if (mRestrictedState.isCsEmergencyRestricted() &&
11820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    !mRestrictedState.isCsNormalRestricted()) {
11830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!newRs.isCsRestricted()) {
11840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove all restriction
11850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_DISABLED);
11860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsRestricted()) {
11870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // enable all restriction
11880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_ENABLED);
11890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsNormalRestricted()) {
11900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove emergency restriction and enable normal restriction
11910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_NORMAL_ENABLED);
11920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
11930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } else if (!mRestrictedState.isCsEmergencyRestricted() &&
11940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    mRestrictedState.isCsNormalRestricted()) {
11950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (!newRs.isCsRestricted()) {
11960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove all restriction
11970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_DISABLED);
11980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsRestricted()) {
11990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // enable all restriction
12000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_ENABLED);
12010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsEmergencyRestricted()) {
12020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // remove normal restriction and enable emergency restriction
12030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_EMERGENCY_ENABLED);
12040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
12050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } else {
12060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (newRs.isCsRestricted()) {
12070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // enable all restriction
12080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_ENABLED);
12090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsEmergencyRestricted()) {
12100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // enable emergency restriction
12110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_EMERGENCY_ENABLED);
12120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                } else if (newRs.isCsNormalRestricted()) {
12130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // enable normal restriction
12140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setNotification(CS_NORMAL_ENABLED);
12150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
12160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
12170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            mRestrictedState = newRs;
12190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
12200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        log("onRestrictedStateChanged: X rs "+ mRestrictedState);
12210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
12220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /** code is registration state 0-5 from TS 27.007 7.2 */
12240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private int regCodeToServiceState(int code) {
12250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        switch (code) {
12260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 0:
12270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 2: // 2 is "searching"
12280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 3: // 3 is "registration denied"
12290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 4: // 4 is "unknown" no vaild in current baseband
12300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 10:// same as 0, but indicates that emergency call is possible.
12310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 12:// same as 2, but indicates that emergency call is possible.
12320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 13:// same as 3, but indicates that emergency call is possible.
12330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 14:// same as 4, but indicates that emergency call is possible.
12340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return ServiceState.STATE_OUT_OF_SERVICE;
12350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 1:
12370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return ServiceState.STATE_IN_SERVICE;
12380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            case 5:
12400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // in service, roam
12410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return ServiceState.STATE_IN_SERVICE;
12420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            default:
12440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                loge("regCodeToServiceState: unexpected service state " + code);
12450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return ServiceState.STATE_OUT_OF_SERVICE;
12460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
12470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
12480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
12510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * code is registration state 0-5 from TS 27.007 7.2
12520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * returns true if registered roam, false otherwise
12530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
12540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean regCodeIsRoaming (int code) {
12550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // 5 is  "in service -- roam"
12560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return 5 == code;
12570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
12580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
12600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Set roaming state when gsmRoaming is true and, if operator mcc is the
12610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * same as sim mcc, ons is different from spn
12620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param gsmRoaming TS 27.007 7.2 CREG registered roaming
12630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param s ServiceState hold current ons
12640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @return true for roaming state set
12650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
12660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean isRoamingBetweenOperators(boolean gsmRoaming, ServiceState s) {
12670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String spn = SystemProperties.get(TelephonyProperties.PROPERTY_ICC_OPERATOR_ALPHA, "empty");
12680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String onsl = s.getOperatorAlphaLong();
12700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String onss = s.getOperatorAlphaShort();
12710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean equalsOnsl = onsl != null && spn.equals(onsl);
12730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean equalsOnss = onss != null && spn.equals(onss);
12740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String simNumeric = SystemProperties.get(
12760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                TelephonyProperties.PROPERTY_ICC_OPERATOR_NUMERIC, "");
12770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        String  operatorNumeric = s.getOperatorNumeric();
12780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        boolean equalsMcc = true;
12800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        try {
12810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            equalsMcc = simNumeric.substring(0, 3).
12820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    equals(operatorNumeric.substring(0, 3));
12830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } catch (Exception e){
12840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
12850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return gsmRoaming && !(equalsMcc && (equalsOnsl || equalsOnss));
12870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
12880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private static int twoDigitsAt(String s, int offset) {
12900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int a, b;
12910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        a = Character.digit(s.charAt(offset), 10);
12930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        b = Character.digit(s.charAt(offset+1), 10);
12940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (a < 0 || b < 0) {
12960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
12970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            throw new RuntimeException("invalid format");
12980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
12990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return a*10 + b;
13010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
13020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
13040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @return The current GPRS state. IN_SERVICE is the same as "attached"
13050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * and OUT_OF_SERVICE is the same as detached.
13060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
13070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    int getCurrentGprsState() {
13080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return gprsState;
13090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
13100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public int getCurrentDataConnectionState() {
13120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return gprsState;
13130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
13140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
13160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @return true if phone is camping on a technology (eg UMTS)
13170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * that could support voice and data simultaneously.
13180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
13190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public boolean isConcurrentVoiceAndDataAllowed() {
13200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return (mRilRadioTechnology >= ServiceState.RIL_RADIO_TECHNOLOGY_UMTS);
13210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
13220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
13240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Provides the name of the algorithmic time zone for the specified
13250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * offset.  Taken from TimeZone.java.
13260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
13270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private static String displayNameFor(int off) {
13280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        off = off / 1000 / 60;
13290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        char[] buf = new char[9];
13310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[0] = 'G';
13320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[1] = 'M';
13330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[2] = 'T';
13340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (off < 0) {
13360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            buf[3] = '-';
13370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            off = -off;
13380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } else {
13390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            buf[3] = '+';
13400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
13410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int hours = off / 60;
13430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int minutes = off % 60;
13440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[4] = (char) ('0' + hours / 10);
13460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[5] = (char) ('0' + hours % 10);
13470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[6] = ':';
13490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[7] = (char) ('0' + minutes / 10);
13510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        buf[8] = (char) ('0' + minutes % 10);
13520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        return new String(buf);
13540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
13550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
13570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * nitzReceiveTime is time_t that the NITZ time was posted
13580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
13590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void setTimeFromNITZString (String nitz, long nitzReceiveTime) {
13600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // "yy/mm/dd,hh:mm:ss(+/-)tz"
13610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        // tz is in number of quarter-hours
13620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        long start = SystemClock.elapsedRealtime();
13640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) {log("NITZ: " + nitz + "," + nitzReceiveTime +
13650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        " start=" + start + " delay=" + (start - nitzReceiveTime));
13660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
13670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        try {
13690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            /* NITZ time (hour:min:sec) will be in UTC but it supplies the timezone
13700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville             * offset as well (which we won't worry about until later) */
13710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            Calendar c = Calendar.getInstance(TimeZone.getTimeZone("GMT"));
13720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.clear();
13740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.DST_OFFSET, 0);
13750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            String[] nitzSubs = nitz.split("[/:,+-]");
13770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int year = 2000 + Integer.parseInt(nitzSubs[0]);
13790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.YEAR, year);
13800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // month is 0 based!
13820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int month = Integer.parseInt(nitzSubs[1]) - 1;
13830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.MONTH, month);
13840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int date = Integer.parseInt(nitzSubs[2]);
13860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.DATE, date);
13870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int hour = Integer.parseInt(nitzSubs[3]);
13890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.HOUR, hour);
13900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int minute = Integer.parseInt(nitzSubs[4]);
13920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.MINUTE, minute);
13930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int second = Integer.parseInt(nitzSubs[5]);
13950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            c.set(Calendar.SECOND, second);
13960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            boolean sign = (nitz.indexOf('-') == -1);
13980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
13990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int tzOffset = Integer.parseInt(nitzSubs[6]);
14000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            int dst = (nitzSubs.length >= 8 ) ? Integer.parseInt(nitzSubs[7])
14020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                              : 0;
14030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // The zone offset received from NITZ is for current local time,
14050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // so DST correction is already applied.  Don't add it again.
14060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            //
14070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // tzOffset += dst * 4;
14080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            //
14090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // We could unapply it if we wanted the raw offset.
14100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            tzOffset = (sign ? 1 : -1) * tzOffset * 15 * 60 * 1000;
14120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            TimeZone    zone = null;
14140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // As a special extension, the Android emulator appends the name of
14160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // the host computer's timezone to the nitz string. this is zoneinfo
14170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // timezone name of the form Area!Location or Area!Location!SubLocation
14180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // so we need to convert the ! into /
14190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (nitzSubs.length >= 9) {
14200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                String  tzname = nitzSubs[8].replace('!','/');
14210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                zone = TimeZone.getTimeZone( tzname );
14220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
14230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            String iso = SystemProperties.get(TelephonyProperties.PROPERTY_OPERATOR_ISO_COUNTRY);
14250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (zone == null) {
14270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (mGotCountryCode) {
14290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (iso != null && iso.length() > 0) {
14300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = TimeUtils.getTimeZone(tzOffset, dst != 0,
14310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                c.getTimeInMillis(),
14320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                iso);
14330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    } else {
14340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // We don't have a valid iso country code.  This is
14350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // most likely because we're on a test network that's
14360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // using a bogus MCC (eg, "001"), so get a TimeZone
14370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // based only on the NITZ parameters.
14380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        zone = getNitzTimeZone(tzOffset, (dst != 0), c.getTimeInMillis());
14390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
14400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
14410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
14420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if ((zone == null) || (mZoneOffset != tzOffset) || (mZoneDst != (dst != 0))){
14440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // We got the time before the country or the zone has changed
14450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // so we don't know how to identify the DST rules yet.  Save
14460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                // the information and hope to fix it up later.
14470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNeedFixZoneAfterNitz = true;
14490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mZoneOffset  = tzOffset;
14500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mZoneDst     = dst != 0;
14510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mZoneTime    = c.getTimeInMillis();
14520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
14530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (zone != null) {
14550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (getAutoTimeZone()) {
14560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setAndBroadcastNetworkSetTimeZone(zone.getID());
14570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
14580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                saveNitzTimeZone(zone.getID());
14590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
14600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            String ignore = SystemProperties.get("gsm.ignore-nitz");
14620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            if (ignore != null && ignore.equals("yes")) {
14630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                log("NITZ: Not setting clock because gsm.ignore-nitz is set");
14640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                return;
14650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
14660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            try {
14680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mWakeLock.acquire();
14690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (getAutoTime()) {
14710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    long millisSinceNitzReceived
14720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            = SystemClock.elapsedRealtime() - nitzReceiveTime;
14730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (millisSinceNitzReceived < 0) {
14750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // Sanity check: something is wrong
14760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) {
14770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            log("NITZ: not setting time, clock has rolled "
14780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                            + "backwards since NITZ time was received, "
14790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                            + nitz);
14800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
14810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        return;
14820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
14830825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (millisSinceNitzReceived > Integer.MAX_VALUE) {
14850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        // If the time is this far off, something is wrong > 24 days!
14860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        if (DBG) {
14870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            log("NITZ: not setting time, processing has taken "
14880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                        + (millisSinceNitzReceived / (1000 * 60 * 60 * 24))
14890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                                        + " days");
14900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        }
14910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        return;
14920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
14930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    // Note: with range checks above, cast to int is safe
14950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    c.add(Calendar.MILLISECOND, (int)millisSinceNitzReceived);
14960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
14970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    if (DBG) {
14980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                        log("NITZ: Setting time of day to " + c.getTime()
14990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            + " NITZ receive delay(ms): " + millisSinceNitzReceived
15000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            + " gained(ms): "
15010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            + (c.getTimeInMillis() - System.currentTimeMillis())
15020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                            + " from " + nitz);
15030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    }
15040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    setAndBroadcastNetworkSetTime(c.getTimeInMillis());
15060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    Log.i(LOG_TAG, "NITZ: after Setting time of day");
15070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
15080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                SystemProperties.set("gsm.nitz.time", String.valueOf(c.getTimeInMillis()));
15090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                saveNitzTime(c.getTimeInMillis());
15100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                if (false) {
15110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    long end = SystemClock.elapsedRealtime();
15120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    log("NITZ: end=" + end + " dur=" + (end - start));
15130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                }
15140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNitzUpdatedTime = true;
15150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            } finally {
15160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mWakeLock.release();
15170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            }
15180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } catch (RuntimeException ex) {
15190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            loge("NITZ: Parsing NITZ time " + nitz + " ex=" + ex);
15200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean getAutoTime() {
15240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        try {
15250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return Settings.System.getInt(phone.getContext().getContentResolver(),
15260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    Settings.System.AUTO_TIME) > 0;
15270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } catch (SettingNotFoundException snfe) {
15280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return true;
15290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private boolean getAutoTimeZone() {
15330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        try {
15340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return Settings.System.getInt(phone.getContext().getContentResolver(),
15350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    Settings.System.AUTO_TIME_ZONE) > 0;
15360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } catch (SettingNotFoundException snfe) {
15370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return true;
15380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void saveNitzTimeZone(String zoneId) {
15420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mSavedTimeZone = zoneId;
15430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void saveNitzTime(long time) {
15460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mSavedTime = time;
15470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mSavedAtTime = SystemClock.elapsedRealtime();
15480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
15510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Set the timezone and send out a sticky broadcast so the system can
15520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * determine if the timezone was set by the carrier.
15530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
15540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param zoneId timezone set by carrier
15550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
15560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void setAndBroadcastNetworkSetTimeZone(String zoneId) {
15570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("setAndBroadcastNetworkSetTimeZone: setTimeZone=" + zoneId);
15580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        AlarmManager alarm =
15590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            (AlarmManager) phone.getContext().getSystemService(Context.ALARM_SERVICE);
15600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        alarm.setTimeZone(zoneId);
15610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Intent intent = new Intent(TelephonyIntents.ACTION_NETWORK_SET_TIMEZONE);
15620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING);
15630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        intent.putExtra("time-zone", zoneId);
15647eff443d1f090abdbbd93eef9f265c74890920bcDianne Hackborn        phone.getContext().sendStickyBroadcastAsUser(intent, UserHandle.ALL);
15650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) {
15660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            log("setAndBroadcastNetworkSetTimeZone: call alarm.setTimeZone and broadcast zoneId=" +
15670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                zoneId);
15680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
15720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Set the time and Send out a sticky broadcast so the system can determine
15730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * if the time was set by the carrier.
15740825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
15750825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param time time set by network
15760825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
15770825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void setAndBroadcastNetworkSetTime(long time) {
15780825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("setAndBroadcastNetworkSetTime: time=" + time + "ms");
15790825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        SystemClock.setCurrentTimeMillis(time);
15800825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Intent intent = new Intent(TelephonyIntents.ACTION_NETWORK_SET_TIME);
15810825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING);
15820825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        intent.putExtra("time", time);
15837eff443d1f090abdbbd93eef9f265c74890920bcDianne Hackborn        phone.getContext().sendStickyBroadcastAsUser(intent, UserHandle.ALL);
15840825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
15850825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
15860825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void revertToNitzTime() {
15870825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (Settings.System.getInt(phone.getContext().getContentResolver(),
15880825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                Settings.System.AUTO_TIME, 0) == 0) {
15890825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return;
15900825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15910825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) {
15920825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            log("Reverting to NITZ Time: mSavedTime=" + mSavedTime
15930825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                + " mSavedAtTime=" + mSavedAtTime);
15940825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15950825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (mSavedTime != 0 && mSavedAtTime != 0) {
15960825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            setAndBroadcastNetworkSetTime(mSavedTime
15970825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                    + (SystemClock.elapsedRealtime() - mSavedAtTime));
15980825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
15990825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
16000825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16010825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void revertToNitzTimeZone() {
16020825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (Settings.System.getInt(phone.getContext().getContentResolver(),
16030825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                Settings.System.AUTO_TIME_ZONE, 0) == 0) {
16040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            return;
16050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
16060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("Reverting to NITZ TimeZone: tz='" + mSavedTimeZone);
16070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (mSavedTimeZone != null) {
16080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            setAndBroadcastNetworkSetTimeZone(mSavedTimeZone);
16090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
16100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
16110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    /**
16130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * Post a notification to NotificationManager for restricted state
16140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     *
16150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     * @param notifyType is one state of PS/CS_*_ENABLE/DISABLE
16160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville     */
16170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private void setNotification(int notifyType) {
16180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("setNotification: create notification " + notifyType);
16200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Context context = phone.getContext();
16210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification = new Notification();
16230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.when = System.currentTimeMillis();
16240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.flags = Notification.FLAG_AUTO_CANCEL;
16250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.icon = com.android.internal.R.drawable.stat_sys_warning;
16260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Intent intent = new Intent();
16270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.contentIntent = PendingIntent
16280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        .getActivity(context, 0, intent, PendingIntent.FLAG_CANCEL_CURRENT);
16290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        CharSequence details = "";
16310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        CharSequence title = context.getText(com.android.internal.R.string.RestrictedChangedTitle);
16320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        int notificationId = CS_NOTIFICATION;
16330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        switch (notifyType) {
16350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case PS_ENABLED:
16360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            notificationId = PS_NOTIFICATION;
16370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            details = context.getText(com.android.internal.R.string.RestrictedOnData);;
16380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case PS_DISABLED:
16400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            notificationId = PS_NOTIFICATION;
16410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case CS_ENABLED:
16430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            details = context.getText(com.android.internal.R.string.RestrictedOnAllVoice);;
16440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case CS_NORMAL_ENABLED:
16460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            details = context.getText(com.android.internal.R.string.RestrictedOnNormal);;
16470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16480825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case CS_EMERGENCY_ENABLED:
16490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            details = context.getText(com.android.internal.R.string.RestrictedOnEmergency);;
16500825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        case CS_DISABLED:
16520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // do nothing and cancel the notification later
16530825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            break;
16540825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
16550825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16560825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (DBG) log("setNotification: put notification " + title + " / " +details);
16570825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.tickerText = title;
16580825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        mNotification.setLatestEventInfo(context, title, details,
16590825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville                mNotification.contentIntent);
16600825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16610825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        NotificationManager notificationManager = (NotificationManager)
16620825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            context.getSystemService(Context.NOTIFICATION_SERVICE);
16630825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16640825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        if (notifyType == PS_DISABLED || notifyType == CS_DISABLED) {
16650825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // cancel previous post notification
16660825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            notificationManager.cancel(notificationId);
16670825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        } else {
16680825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            // update restricted state notification
16690825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville            notificationManager.notify(notificationId, mNotification);
16700825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        }
16710825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
16720825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
16730825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    @Override
1674e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka    protected void onUpdateIccAvailability() {
1675e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka        if (mUiccController == null ) {
1676e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka            return;
1677e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka        }
1678e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka
1679e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        UiccCardApplication newUiccApplication =
1680e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mUiccController.getUiccCardApplication(UiccController.APP_FAM_3GPP);
1681e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka
1682e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        if (mUiccApplcation != newUiccApplication) {
1683e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka            if (mUiccApplcation != null) {
1684e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                log("Removing stale icc objects.");
1685e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mUiccApplcation.unregisterForReady(this);
1686e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                if (mIccRecords != null) {
1687e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                    mIccRecords.unregisterForRecordsLoaded(this);
1688e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                }
1689e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                mIccRecords = null;
1690e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mUiccApplcation = null;
1691e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka            }
1692e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka            if (newUiccApplication != null) {
1693e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                log("New card found");
1694e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mUiccApplcation = newUiccApplication;
1695e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mIccRecords = mUiccApplcation.getIccRecords();
1696e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mUiccApplcation.registerForReady(this, EVENT_SIM_READY, null);
1697e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                if (mIccRecords != null) {
1698e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                    mIccRecords.registerForRecordsLoaded(this, EVENT_SIM_RECORDS_LOADED, null);
1699e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka                }
1700e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka            }
1701e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka        }
1702e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka    }
1703e0e2ebb5a50e580cbe6957dcafb3495a2d0a27f2Alex Yakavenka    @Override
17040825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void log(String s) {
17050825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Log.d(LOG_TAG, "[GsmSST] " + s);
17060825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
17070825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
17080825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    @Override
17090825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    protected void loge(String s) {
17100825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Log.e(LOG_TAG, "[GsmSST] " + s);
17110825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
17120825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
17130825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    private static void sloge(String s) {
17140825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        Log.e(LOG_TAG, "[GsmSST] " + s);
17150825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
17160825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville
17170825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    @Override
17180825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
17190825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println("GsmServiceStateTracker extends:");
17200825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        super.dump(fd, pw, args);
17210825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" phone=" + phone);
17220825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" cellLoc=" + cellLoc);
17230825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" newCellLoc=" + newCellLoc);
17240825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mPreferredNetworkType=" + mPreferredNetworkType);
17250825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" gprsState=" + gprsState);
17260825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" newGPRSState=" + newGPRSState);
17270825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mMaxDataCalls=" + mMaxDataCalls);
17280825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mNewMaxDataCalls=" + mNewMaxDataCalls);
17290825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mReasonDataDenied=" + mReasonDataDenied);
17300825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mNewReasonDataDenied=" + mNewReasonDataDenied);
17310825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mGsmRoaming=" + mGsmRoaming);
17320825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mDataRoaming=" + mDataRoaming);
17330825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mEmergencyOnly=" + mEmergencyOnly);
17340825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mNeedFixZoneAfterNitz=" + mNeedFixZoneAfterNitz);
17350825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mZoneOffset=" + mZoneOffset);
17360825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mZoneDst=" + mZoneDst);
17370825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mZoneTime=" + mZoneTime);
17380825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mGotCountryCode=" + mGotCountryCode);
17390825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mNitzUpdatedTime=" + mNitzUpdatedTime);
17400825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mSavedTimeZone=" + mSavedTimeZone);
17410825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mSavedTime=" + mSavedTime);
17420825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mSavedAtTime=" + mSavedAtTime);
17430825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mStartedGprsRegCheck=" + mStartedGprsRegCheck);
17440825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mReportedGprsNoReg=" + mReportedGprsNoReg);
17450825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mNotification=" + mNotification);
17460825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" mWakeLock=" + mWakeLock);
17470825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" curSpn=" + curSpn);
174860e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        pw.println(" curShowSpn=" + curShowSpn);
17490825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville        pw.println(" curPlmn=" + curPlmn);
175060e7f68c5f73b06fd5b603c331fc24b9d329de6bJohn Wang        pw.println(" curShowPlmn=" + curShowPlmn);
17510825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville    }
17520825495a331bb44df395a0cdb79fab85e68db5d5Wink Saville}
1753