SIMRecords.java revision a1421a82e8d4f711ba13a86d40889868ead492d4
1c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville/*
2c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * Copyright (C) 2006 The Android Open Source Project
3c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville *
4c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * Licensed under the Apache License, Version 2.0 (the "License");
5c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * you may not use this file except in compliance with the License.
6c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * You may obtain a copy of the License at
7c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville *
8c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville *      http://www.apache.org/licenses/LICENSE-2.0
9c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville *
10c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * Unless required by applicable law or agreed to in writing, software
11c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * distributed under the License is distributed on an "AS IS" BASIS,
12c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * See the License for the specific language governing permissions and
14c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * limitations under the License.
15c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville */
16c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
17d720945f2be5ea5fe0faf67e67d9ea0e184eba67Alex Yakavenkapackage com.android.internal.telephony.uicc;
18c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
19c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport android.content.Context;
20c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport android.os.AsyncResult;
21c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport android.os.Message;
22c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport android.os.SystemProperties;
23a8467dd0c524787104b1ccdddc5e8af10ba729edWink Savilleimport android.telephony.TelephonyManager;
2431ae682ff511ddde4073c3f94eff15da2f7fade6Wink Savilleimport android.telephony.PhoneNumberUtils;
25a0d02d50aa0fd7cf1c2d9f4d811efd2e4bfb7d4aJake Hambyimport android.telephony.SmsMessage;
262bc7f2e1da139e183519af01f50940327ca9765eAnju Mathapatiimport android.text.TextUtils;
2799c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Savilleimport android.telephony.Rlog;
286e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seoimport android.content.res.Resources;
29c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
30c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport com.android.internal.telephony.CommandsInterface;
31c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport com.android.internal.telephony.MccTable;
32a0d02d50aa0fd7cf1c2d9f4d811efd2e4bfb7d4aJake Hambyimport com.android.internal.telephony.SmsConstants;
33b9adaa1c4a12df8c8bd44b4803d452662b53e0d8Tom Taylorimport com.android.internal.telephony.SubscriptionController;
34d720945f2be5ea5fe0faf67e67d9ea0e184eba67Alex Yakavenkaimport com.android.internal.telephony.gsm.SimTlv;
35230e46bdd850306dcc54ab6038d4d3132f5032abnfjbimport com.android.internal.telephony.uicc.IccCardApplicationStatus.AppState;
36230e46bdd850306dcc54ab6038d4d3132f5032abnfjbimport com.android.internal.telephony.uicc.IccCardApplicationStatus.AppType;
37c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
3805ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenkaimport java.io.FileDescriptor;
3905ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenkaimport java.io.PrintWriter;
40c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savilleimport java.util.ArrayList;
4105ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenkaimport java.util.Arrays;
42c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
43c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville/**
44c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville * {@hide}
45c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville */
46c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Savillepublic class SIMRecords extends IccRecords {
47cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    protected static final String LOG_TAG = "SIMRecords";
48c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
49c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final boolean CRASH_RIL = false;
50c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
51c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Instance Variables
52c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
53c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    VoiceMailConstants mVmConfig;
54c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
55c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
56c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    SpnOverride mSpnOverride;
57c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
58c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Cached SIM State; cleared on channel close
59c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
6022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    private boolean mCallForwardingEnabled;
61c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
62c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
63c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
64c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * States only used by getSpnFsm FSM
65c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
6622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    private GetSpnFsmState mSpnState;
67c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
68c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /** CPHS service information (See CPHS 4.2 B.3.1.1)
69c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *  It will be set in onSimReady if reading GET_CPHS_INFO successfully
70c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *  mCphsInfo[0] is CPHS Phase
71c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *  mCphsInfo[1] and mCphsInfo[2] is CPHS Service Table
72c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
73c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private byte[] mCphsInfo = null;
74c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    boolean mCspPlmnEnabled = true;
75c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
7622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    byte[] mEfMWIS = null;
7722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    byte[] mEfCPHS_MWI =null;
78c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    byte[] mEfCff = null;
79c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    byte[] mEfCfis = null;
80c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
81230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    byte[] mEfLi = null;
82230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    byte[] mEfPl = null;
83c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
8422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    int mSpnDisplayCondition;
85c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // Numeric network codes listed in TS 51.011 EF[SPDI]
8622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    ArrayList<String> mSpdiNetworks = null;
87c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
8822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    String mPnnHomeName = null;
89c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
90c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    UsimServiceTable mUsimServiceTable;
91c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
92f92cb4bd5519427a0db673709d94683a8baf203aWink Saville    @Override
93f92cb4bd5519427a0db673709d94683a8baf203aWink Saville    public String toString() {
94f92cb4bd5519427a0db673709d94683a8baf203aWink Saville        return "SimRecords: " + super.toString()
95f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mVmConfig" + mVmConfig
96f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mSpnOverride=" + "mSpnOverride"
9722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                + " callForwardingEnabled=" + mCallForwardingEnabled
9822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                + " spnState=" + mSpnState
99f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mCphsInfo=" + mCphsInfo
100f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mCspPlmnEnabled=" + mCspPlmnEnabled
10122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                + " efMWIS=" + mEfMWIS
10222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                + " efCPHS_MWI=" + mEfCPHS_MWI
103f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mEfCff=" + mEfCff
104f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " mEfCfis=" + mEfCfis
105f92cb4bd5519427a0db673709d94683a8baf203aWink Saville                + " getOperatorNumeric=" + getOperatorNumeric();
106f92cb4bd5519427a0db673709d94683a8baf203aWink Saville    }
107f92cb4bd5519427a0db673709d94683a8baf203aWink Saville
108c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Constants
109c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
110c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // From TS 51.011 EF[SPDI] section
111c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int TAG_SPDI = 0xA3;
112c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int TAG_SPDI_PLMN_LIST = 0x80;
113c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
114c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // Full Name IEI from TS 24.008
115c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int TAG_FULL_NETWORK_NAME = 0x43;
116c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
117c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // Short Name IEI from TS 24.008
118c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int TAG_SHORT_NETWORK_NAME = 0x45;
119c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
120c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // active CFF from CPHS 4.2 B.4.5
121c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int CFF_UNCONDITIONAL_ACTIVE = 0x0a;
122c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int CFF_UNCONDITIONAL_DEACTIVE = 0x05;
123c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int CFF_LINE1_MASK = 0x0f;
124c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    static final int CFF_LINE1_RESET = 0xf0;
125c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
126c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // CPHS Service Table (See CPHS 4.2 B.3.1)
127c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int CPHS_SST_MBN_MASK = 0x30;
128c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int CPHS_SST_MBN_ENABLED = 0x30;
129c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
13031ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    // EF_CFIS related constants
13131ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    // Spec reference TS 51.011 section 10.3.46.
13231ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    private static final int CFIS_BCD_NUMBER_LENGTH_OFFSET = 2;
13331ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    private static final int CFIS_TON_NPI_OFFSET = 3;
13431ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    private static final int CFIS_ADN_CAPABILITY_ID_OFFSET = 14;
13531ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    private static final int CFIS_ADN_EXTENSION_ID_OFFSET = 15;
13631ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville
137c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Event Constants
138e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka    private static final int EVENT_GET_IMSI_DONE = 3;
139e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka    private static final int EVENT_GET_ICCID_DONE = 4;
140c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_MBI_DONE = 5;
141c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_MBDN_DONE = 6;
142c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_MWIS_DONE = 7;
143c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_VOICE_MAIL_INDICATOR_CPHS_DONE = 8;
144c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected static final int EVENT_GET_AD_DONE = 9; // Admin data on SIM
145c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected static final int EVENT_GET_MSISDN_DONE = 10;
146c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_CPHS_MAILBOX_DONE = 11;
147c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_SPN_DONE = 12;
148c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_SPDI_DONE = 13;
149c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_UPDATE_DONE = 14;
150c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_PNN_DONE = 15;
151c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected static final int EVENT_GET_SST_DONE = 17;
152c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_ALL_SMS_DONE = 18;
153c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_MARK_SMS_READ_DONE = 19;
154c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_SET_MBDN_DONE = 20;
155c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_SMS_ON_SIM = 21;
156c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_SMS_DONE = 22;
157c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_CFF_DONE = 24;
158c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_SET_CPHS_MAILBOX_DONE = 25;
159c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_INFO_CPHS_DONE = 26;
160cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    // private static final int EVENT_SET_MSISDN_DONE = 30; Defined in IccRecords as 30
161c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_SIM_REFRESH = 31;
162c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_CFIS_DONE = 32;
163c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final int EVENT_GET_CSP_CPHS_DONE = 33;
1642f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim    private static final int EVENT_GET_GID1_DONE = 34;
165230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private static final int EVENT_APP_LOCKED = 35;
1667234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu    private static final int EVENT_GET_GID2_DONE = 36;
167c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
168c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // Lookup table for carriers known to produce SIMs which incorrectly indicate MNC length.
169c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
170c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private static final String[] MCCMNC_CODES_HAVING_3DIGITS_MNC = {
1710530f592d89c1eceea7ee5bccb2359061a04f968duho.ro        "302370", "302720", "310260",
172c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405025", "405026", "405027", "405028", "405029", "405030", "405031", "405032",
173c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405033", "405034", "405035", "405036", "405037", "405038", "405039", "405040",
174c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405041", "405042", "405043", "405044", "405045", "405046", "405047", "405750",
175c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405751", "405752", "405753", "405754", "405755", "405756", "405799", "405800",
176c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405801", "405802", "405803", "405804", "405805", "405806", "405807", "405808",
177c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405809", "405810", "405811", "405812", "405813", "405814", "405815", "405816",
178c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405817", "405818", "405819", "405820", "405821", "405822", "405823", "405824",
179c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405825", "405826", "405827", "405828", "405829", "405830", "405831", "405832",
180c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405833", "405834", "405835", "405836", "405837", "405838", "405839", "405840",
181c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405841", "405842", "405843", "405844", "405845", "405846", "405847", "405848",
182c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405849", "405850", "405851", "405852", "405853", "405875", "405876", "405877",
183c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405878", "405879", "405880", "405881", "405882", "405883", "405884", "405885",
184c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405886", "405908", "405909", "405910", "405911", "405912", "405913", "405914",
185c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405915", "405916", "405917", "405918", "405919", "405920", "405921", "405922",
186c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        "405923", "405924", "405925", "405926", "405927", "405928", "405929", "405930",
1870530f592d89c1eceea7ee5bccb2359061a04f968duho.ro        "405931", "405932", "502142", "502143", "502145", "502146", "502147", "502148"
188c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    };
189c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
190c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Constructor
191c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
192e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka    public SIMRecords(UiccCardApplication app, Context c, CommandsInterface ci) {
193e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        super(app, c, ci);
194c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
19522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mAdnCache = new AdnRecordCache(mFh);
196c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
197c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mVmConfig = new VoiceMailConstants();
198c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mSpnOverride = new SpnOverride();
199c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
20022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsRequested = false;  // No load request is made till SIM ready
201c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
202c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // recordsToLoad is set to 0 because no requests are made yet
20322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad = 0;
204c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
205c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mCi.setOnSmsOnSim(this, EVENT_SMS_ON_SIM, null);
206c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mCi.registerForIccRefresh(this, EVENT_SIM_REFRESH, null);
207c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
208c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Start off by setting empty state
209e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        resetRecords();
210e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        mParentApp.registerForReady(this, EVENT_APP_READY, null);
211230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        mParentApp.registerForLocked(this, EVENT_APP_LOCKED, null);
212f92cb4bd5519427a0db673709d94683a8baf203aWink Saville        if (DBG) log("SIMRecords X ctor this=" + this);
213c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
214c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
215c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
216c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void dispose() {
217f92cb4bd5519427a0db673709d94683a8baf203aWink Saville        if (DBG) log("Disposing SIMRecords this=" + this);
218c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        //Unregister for all events
219c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mCi.unregisterForIccRefresh(this);
220c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mCi.unSetOnSmsOnSim(this);
221e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        mParentApp.unregisterForReady(this);
222230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        mParentApp.unregisterForLocked(this);
223e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        resetRecords();
224c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        super.dispose();
225c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
226c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
227cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
228c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void finalize() {
229c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if(DBG) log("finalized");
230c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
231c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
232e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka    protected void resetRecords() {
233e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        mImsi = null;
23422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mMsisdn = null;
23522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mVoiceMailNum = null;
23622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mMncLength = UNINITIALIZED;
237a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville        log("setting0 mMncLength" + mMncLength);
238b7881d6e7e4e79491376bedf151c3412dfdc4121Wink Saville        mIccId = null;
239c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // -1 means no EF_SPN found; treat accordingly.
24022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mSpnDisplayCondition = -1;
24122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mEfMWIS = null;
24222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mEfCPHS_MWI = null;
24322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mSpdiNetworks = null;
24422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mPnnHomeName = null;
245620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt        mGid1 = null;
2467234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu        mGid2 = null;
247c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
24822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mAdnCache.reset();
249c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
250c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        log("SIMRecords: onRadioOffOrNotAvailable set 'gsm.sim.operator.numeric' to operator=null");
251a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville        log("update icc_operator_numeric=" + null);
252e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu        mTelephonyManager.setSimOperatorNumericForPhone(mParentApp.getPhoneId(), "");
253e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu        mTelephonyManager.setSimOperatorNameForPhone(mParentApp.getPhoneId(), "");
254e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu        mTelephonyManager.setSimCountryIsoForPhone(mParentApp.getPhoneId(), "");
255c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
256c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // recordsRequested is set to false indicating that the SIM
257c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // read requests made so far are not valid. This is set to
258c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // true only when fresh set of read requests are made.
25922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsRequested = false;
260c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
261c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
262c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
263c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    //***** Public Methods
264c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
265c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
266c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * {@inheritDoc}
267c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
268c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
269c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getIMSI() {
270e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        return mImsi;
271c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
272c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
273cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
274c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getMsisdnNumber() {
27522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mMsisdn;
276c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
277c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
278c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
2792f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim    public String getGid1() {
280620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt        return mGid1;
2812f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim    }
2822f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim
2832f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim    @Override
2847234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu    public String getGid2() {
2857234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu        return mGid2;
2867234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu    }
2877234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
2887234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu    @Override
289c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public UsimServiceTable getUsimServiceTable() {
290c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return mUsimServiceTable;
291c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
292c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
293b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja    private int getExtFromEf(int ef) {
294b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        int ext;
295b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        switch (ef) {
296b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja            case EF_MSISDN:
297b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                /* For USIM apps use EXT5. (TS 31.102 Section 4.2.37) */
298b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                if (mParentApp.getType() == AppType.APPTYPE_USIM) {
299b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                    ext = EF_EXT5;
300b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                } else {
301b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                    ext = EF_EXT1;
302b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                }
303b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                break;
304b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja            default:
305b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja                ext = EF_EXT1;
306b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        }
307b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        return ext;
308b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja    }
309b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja
310c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
311c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Set subscriber number to SIM record
312c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
313c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * The subscriber number is stored in EF_MSISDN (TS 51.011)
314c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
315c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * When the operation is complete, onComplete will be sent to its handler
316c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
317c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param alphaTag alpha-tagging of the dailing nubmer (up to 10 characters)
318c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param number dailing nubmer (up to 20 digits)
319c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        if the number starts with '+', then set to international TOA
320c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param onComplete
321c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        onComplete.obj will be an AsyncResult
322c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ((AsyncResult)onComplete.obj).exception == null on success
323c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ((AsyncResult)onComplete.obj).exception != null on fail
324c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
325cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
326c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void setMsisdnNumber(String alphaTag, String number,
327c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            Message onComplete) {
328c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
3296bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        // If the SIM card is locked by PIN, we will set EF_MSISDN fail.
3306bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        // In that case, msisdn and msisdnTag should not be update.
3316bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        mNewMsisdn = number;
3326bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        mNewMsisdnTag = alphaTag;
333c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
3346bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        if(DBG) log("Set MSISDN: " + mNewMsisdnTag + " " + /*mNewMsisdn*/ "xxxxxxx");
335c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
3366bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville        AdnRecord adn = new AdnRecord(mNewMsisdnTag, mNewMsisdn);
337c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
338b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        new AdnRecordLoader(mFh).updateEF(adn, EF_MSISDN, getExtFromEf(EF_MSISDN), 1, null,
339c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                obtainMessage(EVENT_SET_MSISDN_DONE, onComplete));
340c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
341c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
342cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
343c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getMsisdnAlphaTag() {
34422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mMsisdnTag;
345c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
346c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
347cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
348c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getVoiceMailNumber() {
34922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mVoiceMailNum;
350c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
351c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
352c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
353c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Set voice mail number to SIM record
354c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
355c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * The voice mail number can be stored either in EF_MBDN (TS 51.011) or
356c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * EF_MAILBOX_CPHS (CPHS 4.2)
357c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
358c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * If EF_MBDN is available, store the voice mail number to EF_MBDN
359c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
360c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * If EF_MAILBOX_CPHS is enabled, store the voice mail number to EF_CHPS
361c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
362c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * So the voice mail number will be stored in both EFs if both are available
363c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
364c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Return error only if both EF_MBDN and EF_MAILBOX_CPHS fail.
365c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
366c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * When the operation is complete, onComplete will be sent to its handler
367c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
368c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param alphaTag alpha-tagging of the dailing nubmer (upto 10 characters)
369c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param voiceNumber dailing nubmer (upto 20 digits)
370c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        if the number is start with '+', then set to international TOA
371c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param onComplete
372c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        onComplete.obj will be an AsyncResult
373c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ((AsyncResult)onComplete.obj).exception == null on success
374c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ((AsyncResult)onComplete.obj).exception != null on fail
375c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
376cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
377c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void setVoiceMailNumber(String alphaTag, String voiceNumber,
378c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            Message onComplete) {
37922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (mIsVoiceMailFixed) {
380c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            AsyncResult.forMessage((onComplete)).exception =
381c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new IccVmFixedException("Voicemail number is fixed by operator");
382c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            onComplete.sendToTarget();
383c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
384c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
385c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
38622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mNewVoiceMailNum = voiceNumber;
38722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mNewVoiceMailTag = alphaTag;
388c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
38922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        AdnRecord adn = new AdnRecord(mNewVoiceMailTag, mNewVoiceMailNum);
390c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
39122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (mMailboxIndex != 0 && mMailboxIndex != 0xff) {
392c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
393c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            new AdnRecordLoader(mFh).updateEF(adn, EF_MBDN, EF_EXT6,
39422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mMailboxIndex, null,
395c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    obtainMessage(EVENT_SET_MBDN_DONE, onComplete));
396c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
397c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } else if (isCphsMailboxEnabled()) {
398c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
399c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            new AdnRecordLoader(mFh).updateEF(adn, EF_MAILBOX_CPHS,
400c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    EF_EXT1, 1, null,
401c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    obtainMessage(EVENT_SET_CPHS_MAILBOX_DONE, onComplete));
402c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
403c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } else {
404c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            AsyncResult.forMessage((onComplete)).exception =
405c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new IccVmNotSupportedException("Update SIM voice mailbox error");
406c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            onComplete.sendToTarget();
407c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
408c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
409c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
410cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
411c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getVoiceMailAlphaTag()
412c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    {
41322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mVoiceMailTag;
414c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
415c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
416c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
417c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Sets the SIM voice message waiting indicator records
418c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param line GSM Subscriber Profile Number, one-based. Only '1' is supported
419c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param countWaiting The number of messages waiting, if known. Use
420c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *                     -1 to indicate that an unknown number of
421c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *                      messages are waiting
422c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
423cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
424c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void
425c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    setVoiceMessageWaiting(int line, int countWaiting) {
426c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (line != 1) {
427c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // only profile 1 is supported
428c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
429c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
430c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
431c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        try {
43222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            if (mEfMWIS != null) {
433c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // TS 51.011 10.3.45
434c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
435c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // lsb of byte 0 is 'voicemail' status
43622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mEfMWIS[0] = (byte)((mEfMWIS[0] & 0xfe)
43726a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                                    | (countWaiting == 0 ? 0 : 1));
438c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
439c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // byte 1 is the number of voice messages waiting
440c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (countWaiting < 0) {
441c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // The spec does not define what this should be
442c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // if we don't know the count
44322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mEfMWIS[1] = 0;
444c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
44522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mEfMWIS[1] = (byte) countWaiting;
446c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
447c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
448c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.updateEFLinearFixed(
44922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    EF_MWIS, 1, mEfMWIS, null,
45026a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                    obtainMessage (EVENT_UPDATE_DONE, EF_MWIS, 0));
451c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
452c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
45322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            if (mEfCPHS_MWI != null) {
454c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Refer CPHS4_2.WW6 B4.2.3
45522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mEfCPHS_MWI[0] = (byte)((mEfCPHS_MWI[0] & 0xf0)
45626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                            | (countWaiting == 0 ? 0x5 : 0xa));
457c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.updateEFTransparent(
45822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    EF_VOICE_MAIL_INDICATOR_CPHS, mEfCPHS_MWI,
459c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    obtainMessage (EVENT_UPDATE_DONE, EF_VOICE_MAIL_INDICATOR_CPHS));
460c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
461c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } catch (ArrayIndexOutOfBoundsException ex) {
462c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            logw("Error saving voice mail state to SIM. Probably malformed SIM record", ex);
463c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
464c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
465c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
466a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville    // Validate data is !null and the MSP (Multiple Subscriber Profile)
467a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville    // byte is between 1 and 4. See ETSI TS 131 102 v11.3.0 section 4.2.64.
468a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville    private boolean validEfCfis(byte[] data) {
469a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville        return ((data != null) && (data[0] >= 1) && (data[0] <= 4));
470a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville    }
471a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville
47226a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa    public int getVoiceMessageCount() {
47326a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa        boolean voiceMailWaiting = false;
474481a66b57a62b669a4ff3b173f3e96aabec65592Amit Mahajan        int countVoiceMessages = 0;
47526a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa        if (mEfMWIS != null) {
47626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            // Use this data if the EF[MWIS] exists and
47726a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            // has been loaded
47826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            // Refer TS 51.011 Section 10.3.45 for the content description
47926a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            voiceMailWaiting = ((mEfMWIS[0] & 0x01) != 0);
48026a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            countVoiceMessages = mEfMWIS[1] & 0xff;
48126a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa
48226a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            if (voiceMailWaiting && countVoiceMessages == 0) {
48326a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                // Unknown count = -1
48426a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                countVoiceMessages = -1;
48526a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            }
48626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            if(DBG) log(" VoiceMessageCount from SIM MWIS = " + countVoiceMessages);
48726a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa        } else if (mEfCPHS_MWI != null) {
48826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            // use voice mail count from CPHS
48926a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            int indicator = (int) (mEfCPHS_MWI[0] & 0xf);
49026a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa
49126a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            // Refer CPHS4_2.WW6 B4.2.3
49226a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            if (indicator == 0xA) {
49326a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                // Unknown count = -1
49426a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                countVoiceMessages = -1;
49526a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            } else if (indicator == 0x5) {
49626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                countVoiceMessages = 0;
49726a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            }
49826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa            if(DBG) log(" VoiceMessageCount from SIM CPHS = " + countVoiceMessages);
49926a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa        }
50026a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa        return countVoiceMessages;
50126a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa    }
50226a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa
503c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
504c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * {@inheritDoc}
505c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
506c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
507c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public boolean getVoiceCallForwardingFlag() {
50822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mCallForwardingEnabled;
509c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
510c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
511c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
512c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * {@inheritDoc}
513c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
514c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
51531ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville    public void setVoiceCallForwardingFlag(int line, boolean enable, String dialNumber) {
516c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
517c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (line != 1) return; // only line 1 is supported
518c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
51922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mCallForwardingEnabled = enable;
520c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
521c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mRecordsEventsRegistrants.notifyResult(EVENT_CFI);
522c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
523c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        try {
524a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville            if (validEfCfis(mEfCfis)) {
525c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // lsb is of byte 1 is voice status
526c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (enable) {
527c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mEfCfis[1] |= 1;
528c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
529c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mEfCfis[1] &= 0xfe;
530c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
531c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
532a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                log("setVoiceCallForwardingFlag: enable=" + enable
533a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                        + " mEfCfis=" + IccUtils.bytesToHexString(mEfCfis));
534a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville
53531ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                // Update dialNumber if not empty and CFU is enabled.
53631ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                // Spec reference for EF_CFIS contents, TS 51.011 section 10.3.46.
53731ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                if (enable && !TextUtils.isEmpty(dialNumber)) {
53831ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    log("EF_CFIS: updating cf number, " + dialNumber);
53931ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    byte[] bcdNumber = PhoneNumberUtils.numberToCalledPartyBCD(dialNumber);
54031ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville
54131ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    System.arraycopy(bcdNumber, 0, mEfCfis, CFIS_TON_NPI_OFFSET, bcdNumber.length);
54231ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville
54331ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    mEfCfis[CFIS_BCD_NUMBER_LENGTH_OFFSET] = (byte) (bcdNumber.length);
54431ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    mEfCfis[CFIS_ADN_CAPABILITY_ID_OFFSET] = (byte) 0xFF;
54531ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                    mEfCfis[CFIS_ADN_EXTENSION_ID_OFFSET] = (byte) 0xFF;
54631ae682ff511ddde4073c3f94eff15da2f7fade6Wink Saville                }
547c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
548c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.updateEFLinearFixed(
549c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        EF_CFIS, 1, mEfCfis, null,
550c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        obtainMessage (EVENT_UPDATE_DONE, EF_CFIS));
551a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville            } else {
552a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                log("setVoiceCallForwardingFlag: ignoring enable=" + enable
553a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                        + " invalid mEfCfis=" + IccUtils.bytesToHexString(mEfCfis));
554c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
555c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
556c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (mEfCff != null) {
557c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (enable) {
558c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mEfCff[0] = (byte) ((mEfCff[0] & CFF_LINE1_RESET)
559c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            | CFF_UNCONDITIONAL_ACTIVE);
560c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
561c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mEfCff[0] = (byte) ((mEfCff[0] & CFF_LINE1_RESET)
562c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            | CFF_UNCONDITIONAL_DEACTIVE);
563c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
564c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
565c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.updateEFTransparent(
566c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        EF_CFF_CPHS, mEfCff,
567c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        obtainMessage (EVENT_UPDATE_DONE, EF_CFF_CPHS));
568c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
569c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } catch (ArrayIndexOutOfBoundsException ex) {
570e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby            logw("Error saving call forwarding flag to SIM. "
571c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            + "Probably malformed SIM record", ex);
572c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
573c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
574c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
575c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
576c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
577c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Called by STK Service when REFRESH is received.
578c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param fileChanged indicates whether any files changed
579c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param fileList if non-null, a list of EF files that changed
580c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
581cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
582c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void onRefresh(boolean fileChanged, int[] fileList) {
583c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (fileChanged) {
584c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // A future optimization would be to inspect fileList and
585c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // only reload those files that we care about.  For now,
586c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // just re-fetch all SIM records that we cache.
587c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            fetchSimRecords();
588c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
589c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
590c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
591c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
592c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * {@inheritDoc}
593c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
594c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
595c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public String getOperatorNumeric() {
596e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        if (mImsi == null) {
597c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            log("getOperatorNumeric: IMSI == null");
598c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return null;
599c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
60022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (mMncLength == UNINITIALIZED || mMncLength == UNKNOWN) {
601c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            log("getSIMOperatorNumeric: bad mncLength");
602c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return null;
603c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
604c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
605c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Length = length of MCC + length of MNC
606c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // length of mcc = 3 (TS 23.003 Section 2.2)
60722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        return mImsi.substring(0, 3 + mMncLength);
608c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
609c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
610c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    // ***** Overridden from Handler
611cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
612c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void handleMessage(Message msg) {
613c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        AsyncResult ar;
614c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        AdnRecord adn;
615c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
616c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        byte data[];
617c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
618c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        boolean isRecordLoadResponse = false;
619c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
620bb36adde615d3d85fa0fc23935197c6bc6a799edAlex Yakavenka        if (mDestroyed.get()) {
621c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            loge("Received message " + msg + "[" + msg.what + "] " +
622c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    " while being destroyed. Ignoring.");
623c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
624c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
625c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
626c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        try { switch (msg.what) {
627e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka            case EVENT_APP_READY:
628e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                onReady();
629e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                break;
630c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
631230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            case EVENT_APP_LOCKED:
632230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                onLocked();
633230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                break;
634230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
635c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            /* IO events */
636c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_IMSI_DONE:
637c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
638c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
639c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
640c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
641c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
642c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    loge("Exception querying IMSI, Exception:" + ar.exception);
643c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
644c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
645c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
646e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mImsi = (String) ar.result;
647c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
648c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // IMSI (MCC+MNC+MSIN) is at least 6 digits, but not more
649c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // than 15 (and usually 15).
650e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                if (mImsi != null && (mImsi.length() < 6 || mImsi.length() > 15)) {
651e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                    loge("invalid IMSI " + mImsi);
652e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                    mImsi = null;
653c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
654c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
655a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                log("IMSI: mMncLength=" + mMncLength);
656a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                log("IMSI: " + mImsi.substring(0, 6) + "xxxxxxx");
657c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
65822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                if (((mMncLength == UNKNOWN) || (mMncLength == 2)) &&
659e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                        ((mImsi != null) && (mImsi.length() >= 6))) {
660e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                    String mccmncCode = mImsi.substring(0, 6);
661c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    for (String mccmnc : MCCMNC_CODES_HAVING_3DIGITS_MNC) {
662c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        if (mccmnc.equals(mccmncCode)) {
66322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                            mMncLength = 3;
664a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                            log("IMSI: setting1 mMncLength=" + mMncLength);
665c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            break;
666c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        }
667c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
668c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
669c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
67022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                if (mMncLength == UNKNOWN) {
671c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // the SIM has told us all it knows, but it didn't know the mnc length.
672c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // guess using the mcc
673c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    try {
674e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                        int mcc = Integer.parseInt(mImsi.substring(0,3));
67522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mMncLength = MccTable.smallestDigitsMccForMnc(mcc);
676a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                        log("setting2 mMncLength=" + mMncLength);
677c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    } catch (NumberFormatException e) {
67822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mMncLength = UNKNOWN;
679a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                        loge("Corrupt IMSI! setting3 mMncLength=" + mMncLength);
680c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
681c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
682c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
68322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                if (mMncLength != UNKNOWN && mMncLength != UNINITIALIZED) {
684a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                    log("update mccmnc=" + mImsi.substring(0, 3 + mMncLength));
685c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // finally have both the imsi and the mncLength and can parse the imsi properly
686b0b637dbf2a67c0e7eee917c0809f1cc54983986Robert Greenwalt                    MccTable.updateMccMncConfiguration(mContext,
687b0b637dbf2a67c0e7eee917c0809f1cc54983986Robert Greenwalt                            mImsi.substring(0, 3 + mMncLength), false);
688c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
689e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                mImsiReadyRegistrants.notifyRegistrants();
690c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
691c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
692c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_MBI_DONE:
693c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                boolean isValidMbdn;
694c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
695c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
696c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
697c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[]) ar.result;
698c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
699c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isValidMbdn = false;
700c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception == null) {
701c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Refer TS 51.011 Section 10.3.44 for content details
702c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    log("EF_MBI: " + IccUtils.bytesToHexString(data));
703c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
704c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Voice mail record number stored first
70522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mMailboxIndex = data[0] & 0xff;
706c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
707c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // check if dailing numbe id valid
70822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    if (mMailboxIndex != 0 && mMailboxIndex != 0xff) {
709c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        log("Got valid mailbox number for MBDN");
710c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        isValidMbdn = true;
711c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
712c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
713c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
714c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // one more record to load
71522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mRecordsToLoad += 1;
716c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
717c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (isValidMbdn) {
718c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Note: MBDN was not included in NUM_OF_SIM_RECORDS_LOADED
719c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new AdnRecordLoader(mFh).loadFromEF(EF_MBDN, EF_EXT6,
72022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                            mMailboxIndex, obtainMessage(EVENT_GET_MBDN_DONE));
721c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
722c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // If this EF not present, try mailbox as in CPHS standard
723c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // CPHS (CPHS4_2.WW6) is a european standard.
724c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new AdnRecordLoader(mFh).loadFromEF(EF_MAILBOX_CPHS,
725c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            EF_EXT1, 1,
726c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_GET_CPHS_MAILBOX_DONE));
727c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
728c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
729c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
730c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_CPHS_MAILBOX_DONE:
731c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_MBDN_DONE:
732c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                //Resetting the voice mail number and voice mail tag to null
733c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                //as these should be updated from the data read from EF_MBDN.
734c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                //If they are not reset, incase of invalid data/exception these
735c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                //variables are retaining their previous values and are
736c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                //causing invalid voice mailbox info display to user.
73722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mVoiceMailNum = null;
73822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mVoiceMailTag = null;
739c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
740c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
741c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
742c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
743c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
744c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
745c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    log("Invalid or missing EF"
746c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        + ((msg.what == EVENT_GET_CPHS_MAILBOX_DONE) ? "[MAILBOX]" : "[MBDN]"));
747c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
748c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Bug #645770 fall back to CPHS
749c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // FIXME should use SST to decide
750c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
751c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (msg.what == EVENT_GET_MBDN_DONE) {
752c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        //load CPHS on fail...
753c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        // FIXME right now, only load line1's CPHS voice mail entry
754c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
75522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mRecordsToLoad += 1;
756c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        new AdnRecordLoader(mFh).loadFromEF(
757c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                EF_MAILBOX_CPHS, EF_EXT1, 1,
758c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                obtainMessage(EVENT_GET_CPHS_MAILBOX_DONE));
759c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
760c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
761c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
762c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
763c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                adn = (AdnRecord)ar.result;
764c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
765c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("VM: " + adn +
766c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        ((msg.what == EVENT_GET_CPHS_MAILBOX_DONE) ? " EF[MAILBOX]" : " EF[MBDN]"));
767c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
768c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (adn.isEmpty() && msg.what == EVENT_GET_MBDN_DONE) {
769c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // Bug #645770 fall back to CPHS
770c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // FIXME should use SST to decide
771c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // FIXME right now, only load line1's CPHS voice mail entry
77222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mRecordsToLoad += 1;
773c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new AdnRecordLoader(mFh).loadFromEF(
774c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            EF_MAILBOX_CPHS, EF_EXT1, 1,
775c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_GET_CPHS_MAILBOX_DONE));
776c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
777c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
778c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
779c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
78022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mVoiceMailNum = adn.getNumber();
78122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mVoiceMailTag = adn.getAlphaTag();
782c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
783c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
784c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_MSISDN_DONE:
785c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
786c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
787c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
788c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
789c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
790c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    log("Invalid or missing EF[MSISDN]");
791c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
792c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
793c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
794c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                adn = (AdnRecord)ar.result;
795c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
79622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mMsisdn = adn.getNumber();
79722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mMsisdnTag = adn.getAlphaTag();
798c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
79922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                log("MSISDN: " + /*mMsisdn*/ "xxxxxxx");
800c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
801c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
802c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_SET_MSISDN_DONE:
803c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
804c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
805c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
8066bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville                if (ar.exception == null) {
8076bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville                    mMsisdn = mNewMsisdn;
8086bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville                    mMsisdnTag = mNewMsisdnTag;
8096bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville                    log("Success to update EF[MSISDN]");
8106bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville                }
8116bc4098827f3070a44b5e51508b455d7c7be9c07Wink Saville
812c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.userObj != null) {
813c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    AsyncResult.forMessage(((Message) ar.userObj)).exception
814c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            = ar.exception;
815c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    ((Message) ar.userObj).sendToTarget();
816c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
817c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
818c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
819c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_MWIS_DONE:
820c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
821c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
822c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
823c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
824c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
82526a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                if(DBG) log("EF_MWIS : " + IccUtils.bytesToHexString(data));
82626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa
827c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
82826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                    if(DBG) log("EVENT_GET_MWIS_DONE exception = "
82926a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                            + ar.exception);
830c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
831c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
832c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
833c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if ((data[0] & 0xff) == 0xff) {
83426a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                    if(DBG) log("SIMRecords: Uninitialized record MWIS");
835c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
836c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
837c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
83826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                mEfMWIS = data;
83926a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                break;
840c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
841c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_VOICE_MAIL_INDICATOR_CPHS_DONE:
842c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
843c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
844c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
845c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
846c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
84726a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                if(DBG) log("EF_CPHS_MWI: " + IccUtils.bytesToHexString(data));
84826a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa
849c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
85026a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                    if(DBG) log("EVENT_GET_VOICE_MAIL_INDICATOR_CPHS_DONE exception = "
85126a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                            + ar.exception);
852c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
853c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
854c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
85522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mEfCPHS_MWI = data;
85626a4150cfb8cd317eb64994b9d9fd6109bd87ba7Sukanya Rajkhowa                break;
857c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
858c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_ICCID_DONE:
859c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
860c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
861c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
862c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
863c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
864c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
865c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
866c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
867c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
868b7881d6e7e4e79491376bedf151c3412dfdc4121Wink Saville                mIccId = IccUtils.bcdToString(data, 0, data.length);
869c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
870b7881d6e7e4e79491376bedf151c3412dfdc4121Wink Saville                log("iccid: " + mIccId);
871c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
872c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
873c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
874c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
875c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_AD_DONE:
876c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                try {
877c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    isRecordLoadResponse = true;
878c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
879c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    ar = (AsyncResult)msg.obj;
880c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    data = (byte[])ar.result;
881c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
882c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (ar.exception != null) {
883c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        break;
884c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
885c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
886c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    log("EF_AD: " + IccUtils.bytesToHexString(data));
887c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
888c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (data.length < 3) {
889c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        log("Corrupt AD data on SIM");
890c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        break;
891c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
892c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
893c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (data.length == 3) {
894c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        log("MNC length not present in EF_AD");
895c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        break;
896c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
897c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
89822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mMncLength = data[3] & 0xf;
899a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                    log("setting4 mMncLength=" + mMncLength);
900c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
90122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    if (mMncLength == 0xf) {
90222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mMncLength = UNKNOWN;
903a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                        log("setting5 mMncLength=" + mMncLength);
904c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
905c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } finally {
90622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    if (((mMncLength == UNINITIALIZED) || (mMncLength == UNKNOWN) ||
90722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                            (mMncLength == 2)) && ((mImsi != null) && (mImsi.length() >= 6))) {
908e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                        String mccmncCode = mImsi.substring(0, 6);
909a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                        log("mccmncCode=" + mccmncCode);
910c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        for (String mccmnc : MCCMNC_CODES_HAVING_3DIGITS_MNC) {
911c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            if (mccmnc.equals(mccmncCode)) {
91222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                                mMncLength = 3;
913a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                                log("setting6 mMncLength=" + mMncLength);
914c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                break;
915c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            }
916c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        }
917c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
918c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
91922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    if (mMncLength == UNKNOWN || mMncLength == UNINITIALIZED) {
920e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                        if (mImsi != null) {
921c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            try {
922e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                                int mcc = Integer.parseInt(mImsi.substring(0,3));
923c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
92422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                                mMncLength = MccTable.smallestDigitsMccForMnc(mcc);
925a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                                log("setting7 mMncLength=" + mMncLength);
926c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            } catch (NumberFormatException e) {
92722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                                mMncLength = UNKNOWN;
928a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                                loge("Corrupt IMSI! setting8 mMncLength=" + mMncLength);
929c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            }
930c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        } else {
931c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            // Indicate we got this info, but it didn't contain the length.
93222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                            mMncLength = UNKNOWN;
933a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                            log("MNC length not present in EF_AD setting9 mMncLength=" + mMncLength);
934c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        }
935c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
93622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    if (mImsi != null && mMncLength != UNKNOWN) {
937c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        // finally have both imsi and the length of the mnc and can parse
938c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        // the imsi properly
939a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville                        log("update mccmnc=" + mImsi.substring(0, 3 + mMncLength));
940c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        MccTable.updateMccMncConfiguration(mContext,
941b0b637dbf2a67c0e7eee917c0809f1cc54983986Robert Greenwalt                                mImsi.substring(0, 3 + mMncLength), false);
942c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
943c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
944c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
945c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
946c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_SPN_DONE:
947c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
948c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult) msg.obj;
949c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                getSpnFsm(false, ar);
950c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
951c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
952c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_CFF_DONE:
953c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
954c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
955c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult) msg.obj;
956c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[]) ar.result;
957c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
958c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
959c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
960c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
961c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
962c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("EF_CFF_CPHS: " + IccUtils.bytesToHexString(data));
963c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mEfCff = data;
964c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
965e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby                // if EF_CFIS is valid, prefer it to EF_CFF_CPHS
966e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby                if (!validEfCfis(mEfCfis)) {
96722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mCallForwardingEnabled =
968c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        ((data[0] & CFF_LINE1_MASK) == CFF_UNCONDITIONAL_ACTIVE);
969c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
970c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mRecordsEventsRegistrants.notifyResult(EVENT_CFI);
971a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                } else {
972e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby                    log("EVENT_GET_CFF_DONE: EF_CFIS is valid, ignoring EF_CFF_CPHS");
973c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
974c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
975c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
976c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_SPDI_DONE:
977c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
978c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
979c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
980c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
981c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
982c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
983c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
984c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
985c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
986c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                parseEfSpdi(data);
987c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
988c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
989c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_UPDATE_DONE:
990c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
991c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
992c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    logw("update failed. ", ar.exception);
993c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
994c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
995c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
996c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_PNN_DONE:
997c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
998c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
999c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1000c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
1001c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1002c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
1003c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1004c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1005c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1006c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                SimTlv tlv = new SimTlv(data, 0, data.length);
1007c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1008c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                for ( ; tlv.isValidObject() ; tlv.nextObject()) {
1009c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (tlv.getTag() == TAG_FULL_NETWORK_NAME) {
101022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mPnnHomeName
1011c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            = IccUtils.networkNameToString(
1012c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                tlv.getData(), 0, tlv.getData().length);
1013c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        break;
1014c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
1015c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1016c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
1017c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1018c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_ALL_SMS_DONE:
1019c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
1020c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1021c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1022c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null)
1023c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1024c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1025cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville                handleSmses((ArrayList<byte []>) ar.result);
1026c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1027c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1028c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_MARK_SMS_READ_DONE:
102999c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville                Rlog.i("ENF", "marked read: sms " + msg.arg1);
1030c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1031c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1032c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1033c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_SMS_ON_SIM:
1034c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
1035c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1036c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1037c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1038c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                int[] index = (int[])ar.result;
1039c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1040c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null || index.length != 1) {
1041c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    loge("Error on SMS_ON_SIM with exp "
1042c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            + ar.exception + " length " + index.length);
1043c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1044c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    log("READ EF_SMS RECORD index=" + index[0]);
1045c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mFh.loadEFLinearFixed(EF_SMS,index[0],
1046c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_GET_SMS_DONE));
1047c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1048c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1049c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1050c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_SMS_DONE:
1051c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
1052c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1053c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception == null) {
1054c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    handleSms((byte[])ar.result);
1055c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1056c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    loge("Error on GET_SMS with exp " + ar.exception);
1057c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1058c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1059c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_SST_DONE:
1060c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
1061c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1062c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1063c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
1064c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1065c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
1066c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1067c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1068c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1069c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mUsimServiceTable = new UsimServiceTable(data);
1070c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("SST: " + mUsimServiceTable);
1071c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1072c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1073c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_INFO_CPHS_DONE:
1074c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
1075c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1076c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1077c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1078c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
1079c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1080c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1081c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1082c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mCphsInfo = (byte[])ar.result;
1083c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1084c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("iCPHS: " + IccUtils.bytesToHexString(mCphsInfo));
1085c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            break;
1086c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1087c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_SET_MBDN_DONE:
1088c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
1089c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1090c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
10916e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                if (DBG) log("EVENT_SET_MBDN_DONE ex:" + ar.exception);
1092c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception == null) {
109322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mVoiceMailNum = mNewVoiceMailNum;
109422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mVoiceMailTag = mNewVoiceMailTag;
1095c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1096c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1097c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (isCphsMailboxEnabled()) {
109822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    adn = new AdnRecord(mVoiceMailTag, mVoiceMailNum);
1099c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    Message onCphsCompleted = (Message) ar.userObj;
1100c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1101c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    /* write to cphs mailbox whenever it is available but
1102c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    * we only need notify caller once if both updating are
1103c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    * successful.
1104c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    *
1105c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    * so if set_mbdn successful, notify caller here and set
1106c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    * onCphsCompleted to null
1107c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    */
1108c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (ar.exception == null && ar.userObj != null) {
1109c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        AsyncResult.forMessage(((Message) ar.userObj)).exception
1110c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                = null;
1111c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        ((Message) ar.userObj).sendToTarget();
1112c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1113c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        if (DBG) log("Callback with MBDN successful.");
1114c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1115c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        onCphsCompleted = null;
1116c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
1117c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1118c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    new AdnRecordLoader(mFh).
1119c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            updateEF(adn, EF_MAILBOX_CPHS, EF_EXT1, 1, null,
1120c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_SET_CPHS_MAILBOX_DONE,
1121c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                    onCphsCompleted));
1122c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1123c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (ar.userObj != null) {
11246e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                        Resources resource = Resources.getSystem();
11256e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                        if (ar.exception != null && resource.getBoolean(com.android.internal.
11266e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                                    R.bool.editable_voicemailnumber)) {
11276e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                            // GSMPhone will store vm number on device
11286e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                            // when IccVmNotSupportedException occurred
11296e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                            AsyncResult.forMessage(((Message) ar.userObj)).exception
11306e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                                = new IccVmNotSupportedException(
11316e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                                        "Update SIM voice mailbox error");
11326e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                        } else {
11336e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                            AsyncResult.forMessage(((Message) ar.userObj)).exception
1134c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                                = ar.exception;
11356e8a220a642aa479d2f430ff810f4140e80cc2e4giseok.seo                        }
1136c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        ((Message) ar.userObj).sendToTarget();
1137c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    }
1138c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1139c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1140c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_SET_CPHS_MAILBOX_DONE:
1141c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
1142c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1143c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if(ar.exception == null) {
114422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mVoiceMailNum = mNewVoiceMailNum;
114522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mVoiceMailTag = mNewVoiceMailTag;
1146c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1147c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (DBG) log("Set CPHS MailBox with exception: "
1148c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            + ar.exception);
1149c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1150c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.userObj != null) {
1151c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (DBG) log("Callback with CPHS MB successful.");
1152c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    AsyncResult.forMessage(((Message) ar.userObj)).exception
1153c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            = ar.exception;
1154c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    ((Message) ar.userObj).sendToTarget();
1155c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1156c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1157c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_SIM_REFRESH:
1158c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = false;
1159c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1160c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("Sim REFRESH with exception: " + ar.exception);
1161c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception == null) {
1162c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    handleSimRefresh((IccRefreshResponse)ar.result);
1163c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1164c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1165c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_CFIS_DONE:
1166c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
1167c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1168c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1169c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
1170c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1171c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
1172c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1173c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1174c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1175c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("EF_CFIS: " + IccUtils.bytesToHexString(data));
1176c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1177a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                if (validEfCfis(data)) {
1178a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                    mEfCfis = data;
1179c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1180a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                    // Refer TS 51.011 Section 10.3.46 for the content description
118122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mCallForwardingEnabled = ((data[1] & 0x01) != 0);
1182e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby                    log("EF_CFIS: callForwardingEnabled=" + mCallForwardingEnabled);
1183c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1184a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                    mRecordsEventsRegistrants.notifyResult(EVENT_CFI);
1185a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                } else {
1186a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                    log("EF_CFIS: invalid data=" + IccUtils.bytesToHexString(data));
1187a2985af1d00f7db8cb11da3874dc74e0c7ff7088Wink Saville                }
1188c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1189c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1190c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EVENT_GET_CSP_CPHS_DONE:
1191c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                isRecordLoadResponse = true;
1192c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1193c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ar = (AsyncResult)msg.obj;
1194c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1195c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar.exception != null) {
1196c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    loge("Exception in fetching EF_CSP data " + ar.exception);
1197c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    break;
1198c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1199c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1200c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                data = (byte[])ar.result;
1201c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1202c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("EF_CSP: " + IccUtils.bytesToHexString(data));
1203c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                handleEfCspData(data);
1204c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1205c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
12062f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim            case EVENT_GET_GID1_DONE:
12072f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                isRecordLoadResponse = true;
12082f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim
12092f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                ar = (AsyncResult)msg.obj;
12102f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                data =(byte[])ar.result;
12112f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim
12122f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                if (ar.exception != null) {
12132f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                    loge("Exception in get GID1 " + ar.exception);
1214620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt                    mGid1 = null;
12152f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                    break;
12162f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                }
1217620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt                mGid1 = IccUtils.bytesToHexString(data);
1218620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt                log("GID1: " + mGid1);
12192f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim
12202f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim                break;
12212f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim
12227234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu            case EVENT_GET_GID2_DONE:
12237234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                isRecordLoadResponse = true;
12247234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
12257234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                ar = (AsyncResult)msg.obj;
12267234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                data =(byte[])ar.result;
12277234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
12287234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                if (ar.exception != null) {
12297234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                    loge("Exception in get GID2 " + ar.exception);
12307234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                    mGid2 = null;
12317234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                    break;
12327234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                }
12337234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                mGid2 = IccUtils.bytesToHexString(data);
12347234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                log("GID2: " + mGid2);
12357234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
12367234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu                break;
12377234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
1238c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            default:
1239c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                super.handleMessage(msg);   // IccRecords handles generic record load responses
1240c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1241c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }}catch (RuntimeException exc) {
1242c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // I don't want these exceptions to be fatal
1243c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            logw("Exception parsing SIM record", exc);
1244c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } finally {
1245c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // Count up record load responses even if they are fails
1246c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (isRecordLoadResponse) {
1247c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                onRecordLoaded();
1248c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1249c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1250c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1251c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1252230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private class EfPlLoaded implements IccRecordLoaded {
1253230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        public String getEfName() {
1254230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            return "EF_PL";
1255230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1256230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1257230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        public void onRecordLoaded(AsyncResult ar) {
1258230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mEfPl = (byte[]) ar.result;
1259230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            if (DBG) log("EF_PL=" + IccUtils.bytesToHexString(mEfPl));
1260230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1261230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1262230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1263230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private class EfUsimLiLoaded implements IccRecordLoaded {
1264230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        public String getEfName() {
1265230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            return "EF_LI";
1266230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1267230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1268230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        public void onRecordLoaded(AsyncResult ar) {
1269230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mEfLi = (byte[]) ar.result;
1270230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            if (DBG) log("EF_LI=" + IccUtils.bytesToHexString(mEfLi));
1271230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1272230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1273230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1274c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void handleFileUpdate(int efid) {
1275c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        switch(efid) {
1276c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EF_MBDN:
127722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mRecordsToLoad++;
1278c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                new AdnRecordLoader(mFh).loadFromEF(EF_MBDN, EF_EXT6,
127922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                        mMailboxIndex, obtainMessage(EVENT_GET_MBDN_DONE));
1280c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1281c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EF_MAILBOX_CPHS:
128222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mRecordsToLoad++;
1283c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                new AdnRecordLoader(mFh).loadFromEF(EF_MAILBOX_CPHS, EF_EXT1,
1284c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        1, obtainMessage(EVENT_GET_CPHS_MAILBOX_DONE));
1285c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1286c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case EF_CSP_CPHS:
128722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mRecordsToLoad++;
1288c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("[CSP] SIM Refresh for EF_CSP_CPHS");
1289c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.loadEFTransparent(EF_CSP_CPHS,
1290c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        obtainMessage(EVENT_GET_CSP_CPHS_DONE));
1291c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
129267aacea4e6b0199579a71b3a6a2f5d6778b8a002Kevin Li            case EF_FDN:
129367aacea4e6b0199579a71b3a6a2f5d6778b8a002Kevin Li                if (DBG) log("SIM Refresh called for EF_FDN");
129467aacea4e6b0199579a71b3a6a2f5d6778b8a002Kevin Li                mParentApp.queryFdn();
129567aacea4e6b0199579a71b3a6a2f5d6778b8a002Kevin Li                break;
1296fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja            case EF_MSISDN:
1297fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                mRecordsToLoad++;
1298fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                log("SIM Refresh called for EF_MSISDN");
1299fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                new AdnRecordLoader(mFh).loadFromEF(EF_MSISDN, getExtFromEf(EF_MSISDN), 1,
1300fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                        obtainMessage(EVENT_GET_MSISDN_DONE));
1301fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                break;
1302fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja            case EF_CFIS:
1303fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                mRecordsToLoad++;
1304fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                log("SIM Refresh called for EF_CFIS");
1305fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                mFh.loadEFLinearFixed(EF_CFIS,
1306fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                        1, obtainMessage(EVENT_GET_CFIS_DONE));
1307fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                break;
1308fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja            case EF_CFF_CPHS:
1309fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                mRecordsToLoad++;
1310fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                log("SIM Refresh called for EF_CFF_CPHS");
1311fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                mFh.loadEFTransparent(EF_CFF_CPHS,
1312fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                        obtainMessage(EVENT_GET_CFF_DONE));
1313fcc95e67fce873f3f303cc2dee284ce437295783Preeti Ahuja                break;
1314c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            default:
1315c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // For now, fetch all records if this is not a
1316c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // voicemail number.
1317c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // TODO: Handle other cases, instead of fetching all.
131822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mAdnCache.reset();
1319c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                fetchSimRecords();
1320c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1321c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1322c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1323c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1324c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void handleSimRefresh(IccRefreshResponse refreshResponse){
1325c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (refreshResponse == null) {
1326c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (DBG) log("handleSimRefresh received without input");
1327c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
1328c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1329c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1330c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (refreshResponse.aid != null &&
1331e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka                !refreshResponse.aid.equals(mParentApp.getAid())) {
1332c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // This is for different app. Ignore.
1333c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
1334c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1335c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1336c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        switch (refreshResponse.refreshResult) {
1337c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case IccRefreshResponse.REFRESH_RESULT_FILE_UPDATE:
1338c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("handleSimRefresh with SIM_FILE_UPDATED");
1339c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                handleFileUpdate(refreshResponse.efId);
1340c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1341c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case IccRefreshResponse.REFRESH_RESULT_INIT:
1342c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("handleSimRefresh with SIM_REFRESH_INIT");
1343c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // need to reload all files (that we care about)
134464bfd98578babdd437f1a83d2d5e1fc92c76e729Alex Yakavenka                onIccRefreshInit();
1345c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1346c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case IccRefreshResponse.REFRESH_RESULT_RESET:
134762648296ee1514d871d7d779d6f33da5e55babcaShishir Agrawal                // Refresh reset is handled by the UiccCard object.
1348c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("handleSimRefresh with SIM_REFRESH_RESET");
1349c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1350c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            default:
1351c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // unknown refresh operation
1352c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (DBG) log("handleSimRefresh with unknown operation");
1353c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1354c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1355c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1356c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1357c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1358e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby     * Dispatch 3GPP format message to registrant ({@code GSMPhone} or {@code CDMALTEPhone})
1359e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby     * to pass to the 3GPP SMS dispatcher for delivery.
1360c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1361a0d02d50aa0fd7cf1c2d9f4d811efd2e4bfb7d4aJake Hamby    private int dispatchGsmMessage(SmsMessage message) {
1362c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mNewSmsRegistrants.notifyResult(message);
1363c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return 0;
1364c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1365c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1366c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void handleSms(byte[] ba) {
1367c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (ba[0] != 0)
136899c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville            Rlog.d("ENF", "status : " + ba[0]);
1369c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1370c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // 3GPP TS 51.011 v5.0.0 (20011-12)  10.5.3
1371c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // 3 == "received by MS from network; message to be read"
1372c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (ba[0] == 3) {
1373c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            int n = ba.length;
1374c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1375c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // Note: Data may include trailing FF's.  That's OK; message
1376c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // should still parse correctly.
1377c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            byte[] pdu = new byte[n - 1];
1378c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            System.arraycopy(ba, 1, pdu, 0, n - 1);
1379a0d02d50aa0fd7cf1c2d9f4d811efd2e4bfb7d4aJake Hamby            SmsMessage message = SmsMessage.createFromPdu(pdu, SmsConstants.FORMAT_3GPP);
1380c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1381c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            dispatchGsmMessage(message);
1382c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1383c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1384c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1385c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1386cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    private void handleSmses(ArrayList<byte[]> messages) {
1387c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        int count = messages.size();
1388c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1389c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        for (int i = 0; i < count; i++) {
1390cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville            byte[] ba = messages.get(i);
1391c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1392c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (ba[0] != 0)
139399c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville                Rlog.i("ENF", "status " + i + ": " + ba[0]);
1394c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1395c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // 3GPP TS 51.011 v5.0.0 (20011-12)  10.5.3
1396c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // 3 == "received by MS from network; message to be read"
1397c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1398c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (ba[0] == 3) {
1399c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                int n = ba.length;
1400c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1401c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // Note: Data may include trailing FF's.  That's OK; message
1402c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // should still parse correctly.
1403c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                byte[] pdu = new byte[n - 1];
1404c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                System.arraycopy(ba, 1, pdu, 0, n - 1);
1405a0d02d50aa0fd7cf1c2d9f4d811efd2e4bfb7d4aJake Hamby                SmsMessage message = SmsMessage.createFromPdu(pdu, SmsConstants.FORMAT_3GPP);
1406c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1407c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                dispatchGsmMessage(message);
1408c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1409c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // 3GPP TS 51.011 v5.0.0 (20011-12)  10.5.3
1410c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // 1 == "received by MS from network; message read"
1411c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1412c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                ba[0] = 1;
1413c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1414cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville                if (false) { // FIXME: writing seems to crash RdoServD
1415c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mFh.updateEFLinearFixed(EF_SMS,
1416c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            i, ba, null, obtainMessage(EVENT_MARK_SMS_READ_DONE, i));
1417c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1418c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1419c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1420c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1421c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1422230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private String findBestLanguage(byte[] languages) {
1423230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        String bestMatch = null;
1424230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        String[] locales = mContext.getAssets().getLocales();
1425230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1426230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if ((languages == null) || (locales == null)) return null;
1427230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1428230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        // Each 2-bytes consists of one language
1429230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        for (int i = 0; (i + 1) < languages.length; i += 2) {
1430230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            try {
1431230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                String lang = new String(languages, i, 2, "ISO-8859-1");
1432230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                if (DBG) log ("languages from sim = " + lang);
1433230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                for (int j = 0; j < locales.length; j++) {
1434230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                    if (locales[j] != null && locales[j].length() >= 2 &&
1435230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                            locales[j].substring(0, 2).equalsIgnoreCase(lang)) {
1436230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                        return lang;
1437230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                    }
1438230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                }
1439230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                if (bestMatch != null) break;
1440230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            } catch(java.io.UnsupportedEncodingException e) {
1441230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                log ("Failed to parse USIM language records" + e);
1442230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            }
1443230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1444230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        // no match found. return null
1445230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        return null;
1446230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1447230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1448230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private void setLocaleFromUsim() {
1449230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        String prefLang = null;
1450230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        // check EFli then EFpl
1451230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        prefLang = findBestLanguage(mEfLi);
1452230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1453230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if (prefLang == null) {
1454230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            prefLang = findBestLanguage(mEfPl);
1455230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1456230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1457230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if (prefLang != null) {
1458230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            // check country code from SIM
1459230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            String imsi = getIMSI();
1460230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            String country = null;
1461230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            if (imsi != null) {
1462230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                country = MccTable.countryCodeForMcc(
1463230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                                    Integer.parseInt(imsi.substring(0,3)));
1464230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            }
1465230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            if (DBG) log("Setting locale to " + prefLang + "_" + country);
1466230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            MccTable.setSystemLocale(mContext, prefLang, country);
1467230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        } else {
1468230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            if (DBG) log ("No suitable USIM selected locale");
1469230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1470230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1471230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1472cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
1473c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void onRecordLoaded() {
1474c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // One record loaded successfully or failed, In either case
1475c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // we need to update the recordsToLoad count
147622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad -= 1;
147722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (DBG) log("onRecordLoaded " + mRecordsToLoad + " requested: " + mRecordsRequested);
1478c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
147922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (mRecordsToLoad == 0 && mRecordsRequested == true) {
1480c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            onAllRecordsLoaded();
148122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        } else if (mRecordsToLoad < 0) {
1482c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            loge("recordsToLoad <0, programmer error suspected");
148322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            mRecordsToLoad = 0;
1484c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1485c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1486c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1487cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
1488c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void onAllRecordsLoaded() {
1489e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        if (DBG) log("record load complete");
1490c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1491230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        setLocaleFromUsim();
1492230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1493230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if (mParentApp.getState() == AppState.APPSTATE_PIN ||
1494230e46bdd850306dcc54ab6038d4d3132f5032abnfjb               mParentApp.getState() == AppState.APPSTATE_PUK) {
1495230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            // reset recordsRequested, since sim is not loaded really
1496230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mRecordsRequested = false;
1497230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            // lock state, only update language
1498230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            return ;
1499230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1500230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1501c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Some fields require more than one SIM record to set
1502c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1503e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        String operator = getOperatorNumeric();
1504e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        if (!TextUtils.isEmpty(operator)) {
1505e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville            log("onAllRecordsLoaded set 'gsm.sim.operator.numeric' to operator='" +
1506e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville                    operator + "'");
1507a8467dd0c524787104b1ccdddc5e8af10ba729edWink Saville            log("update icc_operator_numeric=" + operator);
1508e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu            mTelephonyManager.setSimOperatorNumericForPhone(
1509e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mParentApp.getPhoneId(), operator);
1510b9adaa1c4a12df8c8bd44b4803d452662b53e0d8Tom Taylor            final SubscriptionController subController = SubscriptionController.getInstance();
1511b9adaa1c4a12df8c8bd44b4803d452662b53e0d8Tom Taylor            subController.setMccMnc(operator, subController.getDefaultSmsSubId());
1512e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        } else {
1513e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville            log("onAllRecordsLoaded empty 'gsm.sim.operator.numeric' skipping");
1514e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        }
1515c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1516e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        if (!TextUtils.isEmpty(mImsi)) {
1517a1421a82e8d4f711ba13a86d40889868ead492d4Amit Mahajan            log("onAllRecordsLoaded set mcc imsi" + (VDBG ? ("=" + mImsi) : ""));
1518e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu            mTelephonyManager.setSimCountryIsoForPhone(
1519e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mParentApp.getPhoneId(), MccTable.countryCodeForMcc(
1520e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    Integer.parseInt(mImsi.substring(0,3))));
1521e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville        } else {
1522e9070e6d48d1389987650fa2c3e1f90aab860684Wink Saville            log("onAllRecordsLoaded empty imsi skipping setting mcc");
1523c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1524c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1525c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        setVoiceMailByCountry(operator);
1526c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        setSpnFromConfig(operator);
1527c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1528b7881d6e7e4e79491376bedf151c3412dfdc4121Wink Saville        mRecordsLoadedRegistrants.notifyRegistrants(
1529c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            new AsyncResult(null, null, null));
1530c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1531c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1532c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    //***** Private methods
1533c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1534c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void setSpnFromConfig(String carrier) {
1535c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (mSpnOverride.containsCarrier(carrier)) {
1536b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal            setServiceProviderName(mSpnOverride.getSpn(carrier));
1537e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu            mTelephonyManager.setSimOperatorNameForPhone(
1538e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mParentApp.getPhoneId(), getServiceProviderName());
1539c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1540c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1541c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1542c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1543c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void setVoiceMailByCountry (String spn) {
1544c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (mVmConfig.containsCarrier(spn)) {
154522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            mIsVoiceMailFixed = true;
154622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            mVoiceMailNum = mVmConfig.getVoiceMailNumber(spn);
154722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            mVoiceMailTag = mVmConfig.getVoiceMailTag(spn);
1548c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1549c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1550c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1551c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
1552c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public void onReady() {
1553c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        fetchSimRecords();
1554c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1555c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1556230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private void onLocked() {
1557230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if (DBG) log("only fetch EF_LI and EF_PL in lock state");
1558230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        loadEfLiAndEfPl();
1559230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1560230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1561230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    private void loadEfLiAndEfPl() {
1562e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro        Resources resource = Resources.getSystem();
1563e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro        if (!resource.getBoolean(com.android.internal.R.bool.config_use_sim_language_file)) {
1564e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro            if (DBG) log ("Not using EF LI/EF PL");
1565e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro            return;
1566e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro        }
1567e409b02a691d5bb0515aab41cfa597c725eb9174duho.ro
1568230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        if (mParentApp.getType() == AppType.APPTYPE_USIM) {
1569ab55739495b38cf403e7c4514e00f4661034c838Amit Mahajan            mRecordsRequested = true;
1570230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mFh.loadEFTransparent(EF_LI,
1571230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                    obtainMessage(EVENT_GET_ICC_RECORD_DONE, new EfUsimLiLoaded()));
1572230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mRecordsToLoad++;
1573230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1574230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mFh.loadEFTransparent(EF_PL,
1575230e46bdd850306dcc54ab6038d4d3132f5032abnfjb                    obtainMessage(EVENT_GET_ICC_RECORD_DONE, new EfPlLoaded()));
1576230e46bdd850306dcc54ab6038d4d3132f5032abnfjb            mRecordsToLoad++;
1577230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        }
1578230e46bdd850306dcc54ab6038d4d3132f5032abnfjb    }
1579230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1580c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void fetchSimRecords() {
158122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsRequested = true;
1582c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
158322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (DBG) log("fetchSimRecords " + mRecordsToLoad);
1584c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1585e287feac673ff68565b766e0e463d105fa9cef9dAlex Yakavenka        mCi.getIMSIForApp(mParentApp.getAid(), obtainMessage(EVENT_GET_IMSI_DONE));
158622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1587c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1588c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_ICCID, obtainMessage(EVENT_GET_ICCID_DONE));
158922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1590c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1591c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // FIXME should examine EF[MSISDN]'s capability configuration
1592c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // to determine which is the voice/data/fax line
1593b66ae5f6334393d39becc860840ab42a90c9a926Preeti Ahuja        new AdnRecordLoader(mFh).loadFromEF(EF_MSISDN, getExtFromEf(EF_MSISDN), 1,
1594c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    obtainMessage(EVENT_GET_MSISDN_DONE));
159522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1596c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1597c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Record number is subscriber profile
1598c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFLinearFixed(EF_MBI, 1, obtainMessage(EVENT_GET_MBI_DONE));
159922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1600c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1601c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_AD, obtainMessage(EVENT_GET_AD_DONE));
160222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1603c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1604c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Record number is subscriber profile
1605c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFLinearFixed(EF_MWIS, 1, obtainMessage(EVENT_GET_MWIS_DONE));
160622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1607c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1608c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1609c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Also load CPHS-style voice mail indicator, which stores
1610c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // the same info as EF[MWIS]. If both exist, both are updated
1611c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // but the EF[MWIS] data is preferred
1612c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Please note this must be loaded after EF[MWIS]
1613c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(
1614c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                EF_VOICE_MAIL_INDICATOR_CPHS,
1615c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                obtainMessage(EVENT_GET_VOICE_MAIL_INDICATOR_CPHS_DONE));
161622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1617c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1618c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Same goes for Call Forward Status indicator: fetch both
1619c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // EF[CFIS] and CPHS-EF, with EF[CFIS] preferred.
1620c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFLinearFixed(EF_CFIS, 1, obtainMessage(EVENT_GET_CFIS_DONE));
162122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1622c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_CFF_CPHS, obtainMessage(EVENT_GET_CFF_DONE));
162322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1624c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1625c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1626c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        getSpnFsm(true, null);
1627c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1628c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_SPDI, obtainMessage(EVENT_GET_SPDI_DONE));
162922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1630c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1631c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFLinearFixed(EF_PNN, 1, obtainMessage(EVENT_GET_PNN_DONE));
163222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1633c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1634c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_SST, obtainMessage(EVENT_GET_SST_DONE));
163522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1636c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1637c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_INFO_CPHS, obtainMessage(EVENT_GET_INFO_CPHS_DONE));
163822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1639c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1640c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mFh.loadEFTransparent(EF_CSP_CPHS,obtainMessage(EVENT_GET_CSP_CPHS_DONE));
164122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mRecordsToLoad++;
1642c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
16432f837b8058eba0bc59e983c67efbc00cd9a80eeeHyejin Kim        mFh.loadEFTransparent(EF_GID1, obtainMessage(EVENT_GET_GID1_DONE));
1644620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt        mRecordsToLoad++;
1645c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
16467234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu        mFh.loadEFTransparent(EF_GID2, obtainMessage(EVENT_GET_GID2_DONE));
16477234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu        mRecordsToLoad++;
16487234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu
1649230e46bdd850306dcc54ab6038d4d3132f5032abnfjb        loadEfLiAndEfPl();
1650230e46bdd850306dcc54ab6038d4d3132f5032abnfjb
1651c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // XXX should seek instead of examining them all
1652c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (false) { // XXX
1653c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            mFh.loadEFLinearFixedAll(EF_SMS, obtainMessage(EVENT_GET_ALL_SMS_DONE));
165422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            mRecordsToLoad++;
1655c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1656c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1657c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (CRASH_RIL) {
1658c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            String sms = "0107912160130310f20404d0110041007030208054832b0120"
1659c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                         + "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1660c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                         + "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1661c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                         + "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1662c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                         + "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1663c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                         + "ffffffffffffffffffffffffffffff";
1664c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            byte[] ba = IccUtils.hexStringToBytes(sms);
1665c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1666c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            mFh.updateEFLinearFixed(EF_SMS, 1, ba, null,
1667c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_MARK_SMS_READ_DONE, 1));
1668c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
166922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (DBG) log("fetchSimRecords " + mRecordsToLoad + " requested: " + mRecordsRequested);
1670c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1671c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1672c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1673c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Returns the SpnDisplayRule based on settings on the SIM and the
1674c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * specified plmn (currently-registered PLMN).  See TS 22.101 Annex A
1675c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * and TS 51.011 10.3.11 for details.
1676c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
16772bc7f2e1da139e183519af01f50940327ca9765eAnju Mathapati     * If the SPN is not found on the SIM or is empty, the rule is
16782bc7f2e1da139e183519af01f50940327ca9765eAnju Mathapati     * always PLMN_ONLY.
1679c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1680c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    @Override
1681c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public int getDisplayRule(String plmn) {
1682c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        int rule;
1683be6c87905a15d1e36e87189ad7df5d5a72a52f69Shishir Agrawal
168462d026a3882d133aa81995f8dfd2c1d25b1b0649Shishir Agrawal        if (mParentApp != null && mParentApp.getUiccCard() != null &&
168568515b655255005f653aec29e9f152412514982aShishir Agrawal            mParentApp.getUiccCard().getOperatorBrandOverride() != null) {
1686be6c87905a15d1e36e87189ad7df5d5a72a52f69Shishir Agrawal        // If the operator has been overridden, treat it as the SPN file on the SIM did not exist.
1687be6c87905a15d1e36e87189ad7df5d5a72a52f69Shishir Agrawal            rule = SPN_RULE_SHOW_PLMN;
1688be6c87905a15d1e36e87189ad7df5d5a72a52f69Shishir Agrawal        } else if (TextUtils.isEmpty(getServiceProviderName()) || mSpnDisplayCondition == -1) {
16892bc7f2e1da139e183519af01f50940327ca9765eAnju Mathapati            // No EF_SPN content was found on the SIM, or not yet loaded.  Just show ONS.
1690c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            rule = SPN_RULE_SHOW_PLMN;
1691c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } else if (isOnMatchingPlmn(plmn)) {
1692c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            rule = SPN_RULE_SHOW_SPN;
169322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            if ((mSpnDisplayCondition & 0x01) == 0x01) {
1694c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // ONS required when registered to HPLMN or PLMN in EF_SPDI
1695c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                rule |= SPN_RULE_SHOW_PLMN;
1696c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1697c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        } else {
1698c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            rule = SPN_RULE_SHOW_PLMN;
169922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            if ((mSpnDisplayCondition & 0x02) == 0x00) {
1700c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // SPN required if not registered to HPLMN or PLMN in EF_SPDI
1701c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                rule |= SPN_RULE_SHOW_SPN;
1702c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1703c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1704c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return rule;
1705c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1706c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1707c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1708c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Checks if plmn is HPLMN or on the spdiNetworks list.
1709c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1710c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private boolean isOnMatchingPlmn(String plmn) {
1711c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (plmn == null) return false;
1712c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1713c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (plmn.equals(getOperatorNumeric())) {
1714c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return true;
1715c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1716c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
171722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        if (mSpdiNetworks != null) {
171822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            for (String spdiNet : mSpdiNetworks) {
1719c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (plmn.equals(spdiNet)) {
1720c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    return true;
1721c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1722c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1723c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1724c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return false;
1725c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1726c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1727c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1728c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * States of Get SPN Finite State Machine which only used by getSpnFsm()
1729c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
173022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville    private enum GetSpnFsmState {
1731c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        IDLE,               // No initialized
1732c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        INIT,               // Start FSM
1733c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        READ_SPN_3GPP,      // Load EF_SPN firstly
1734c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        READ_SPN_CPHS,      // Load EF_SPN_CPHS secondly
1735c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        READ_SPN_SHORT_CPHS // Load EF_SPN_SHORT_CPHS last
1736c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1737c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1738c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1739c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Finite State Machine to load Service Provider Name , which can be stored
1740c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * in either EF_SPN (3GPP), EF_SPN_CPHS, or EF_SPN_SHORT_CPHS (CPHS4.2)
1741c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
1742c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * After starting, FSM will search SPN EFs in order and stop after finding
1743c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * the first valid SPN
1744c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
1745c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * If the FSM gets restart while waiting for one of
1746c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * SPN EFs results (i.e. a SIM refresh occurs after issuing
1747c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * read EF_CPHS_SPN), it will re-initialize only after
1748c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * receiving and discarding the unfinished SPN EF result.
1749c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
1750c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param start set true only for initialize loading
1751c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param ar the AsyncResult from loadEFTransparent
1752c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ar.exception holds exception in error
1753c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *        ar.result is byte[] for data in success
1754c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1755c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void getSpnFsm(boolean start, AsyncResult ar) {
1756c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        byte[] data;
1757c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1758c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (start) {
1759c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // Check previous state to see if there is outstanding
1760c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // SPN read
176122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville            if(mSpnState == GetSpnFsmState.READ_SPN_3GPP ||
176222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville               mSpnState == GetSpnFsmState.READ_SPN_CPHS ||
176322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville               mSpnState == GetSpnFsmState.READ_SPN_SHORT_CPHS ||
176422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville               mSpnState == GetSpnFsmState.INIT) {
1765c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // Set INIT then return so the INIT code
1766c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                // will run when the outstanding read done.
176722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpnState = GetSpnFsmState.INIT;
1768c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                return;
1769c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            } else {
177022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpnState = GetSpnFsmState.INIT;
1771c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1772c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1773c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
177422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        switch(mSpnState){
1775c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case INIT:
1776b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                setServiceProviderName(null);
1777c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1778c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                mFh.loadEFTransparent(EF_SPN,
1779c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                        obtainMessage(EVENT_GET_SPN_DONE));
178022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mRecordsToLoad++;
1781c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
178222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpnState = GetSpnFsmState.READ_SPN_3GPP;
1783c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1784c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case READ_SPN_3GPP:
1785c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar != null && ar.exception == null) {
1786c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    data = (byte[]) ar.result;
178722d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnDisplayCondition = 0xff & data[0];
1788b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    setServiceProviderName(IccUtils.adnStringFieldToString(
1789b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                            data, 1, data.length - 1));
1790c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1791b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    if (DBG) log("Load EF_SPN: " + getServiceProviderName()
179222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                            + " spnDisplayCondition: " + mSpnDisplayCondition);
1793e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mTelephonyManager.setSimOperatorNameForPhone(
1794e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                            mParentApp.getPhoneId(), getServiceProviderName());
1795c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
179622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnState = GetSpnFsmState.IDLE;
1797c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1798c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mFh.loadEFTransparent( EF_SPN_CPHS,
1799c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            obtainMessage(EVENT_GET_SPN_DONE));
180022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mRecordsToLoad++;
1801c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
180222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnState = GetSpnFsmState.READ_SPN_CPHS;
1803c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1804c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // See TS 51.011 10.3.11.  Basically, default to
1805c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    // show PLMN always, and SPN also if roaming.
180622d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnDisplayCondition = -1;
1807c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1808c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1809c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case READ_SPN_CPHS:
1810c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar != null && ar.exception == null) {
1811c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    data = (byte[]) ar.result;
1812b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    setServiceProviderName(IccUtils.adnStringFieldToString(data, 0, data.length));
1813c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1814b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    if (DBG) log("Load EF_SPN_CPHS: " + getServiceProviderName());
1815e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mTelephonyManager.setSimOperatorNameForPhone(
1816e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                            mParentApp.getPhoneId(), getServiceProviderName());
1817c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
181822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnState = GetSpnFsmState.IDLE;
1819c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                } else {
1820c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    mFh.loadEFTransparent(
1821c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                            EF_SPN_SHORT_CPHS, obtainMessage(EVENT_GET_SPN_DONE));
182222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mRecordsToLoad++;
1823c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
182422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                    mSpnState = GetSpnFsmState.READ_SPN_SHORT_CPHS;
1825c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1826c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1827c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            case READ_SPN_SHORT_CPHS:
1828c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                if (ar != null && ar.exception == null) {
1829c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    data = (byte[]) ar.result;
1830b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    setServiceProviderName(IccUtils.adnStringFieldToString(data, 0, data.length));
1831c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1832b93bb3538c55f173f94a4ee7510d9d1521d8f731Shishir Agrawal                    if (DBG) log("Load EF_SPN_SHORT_CPHS: " + getServiceProviderName());
1833e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                    mTelephonyManager.setSimOperatorNameForPhone(
1834e70617d81dcd42350a737b11c25532e1d43df4ffLegler Wu                            mParentApp.getPhoneId(), getServiceProviderName());
1835c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }else {
1836c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                    if (DBG) log("No SPN loaded in either CHPS or 3GPP");
1837c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                }
1838c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
183922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpnState = GetSpnFsmState.IDLE;
1840c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1841c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            default:
184222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpnState = GetSpnFsmState.IDLE;
1843c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1844c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1845c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1846c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1847c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Parse TS 51.011 EF[SPDI] record
1848c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * This record contains the list of numeric network IDs that
1849c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * are treated specially when determining SPN display
1850c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1851c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void
1852c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    parseEfSpdi(byte[] data) {
1853c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        SimTlv tlv = new SimTlv(data, 0, data.length);
1854c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1855c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        byte[] plmnEntries = null;
1856c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1857c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        for ( ; tlv.isValidObject() ; tlv.nextObject()) {
1858c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // Skip SPDI tag, if existant
1859c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (tlv.getTag() == TAG_SPDI) {
1860c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville              tlv = new SimTlv(tlv.getData(), 0, tlv.getData().length);
1861c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1862c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // There should only be one TAG_SPDI_PLMN_LIST
1863c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (tlv.getTag() == TAG_SPDI_PLMN_LIST) {
1864c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                plmnEntries = tlv.getData();
1865c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                break;
1866c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1867c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1868c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1869c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (plmnEntries == null) {
1870c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            return;
1871c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1872c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
187322d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        mSpdiNetworks = new ArrayList<String>(plmnEntries.length / 3);
1874c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1875c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        for (int i = 0 ; i + 2 < plmnEntries.length ; i += 3) {
1876c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            String plmnCode;
1877c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            plmnCode = IccUtils.bcdToString(plmnEntries, i, 3);
1878c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1879c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            // Valid operator codes are 5 or 6 digits
1880c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            if (plmnCode.length() >= 5) {
1881c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                log("EF_SPDI network: " + plmnCode);
188222d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville                mSpdiNetworks.add(plmnCode);
1883c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville            }
1884c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1885c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1886c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1887c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1888c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * check to see if Mailbox Number is allocated and activated in CPHS SST
1889c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1890c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private boolean isCphsMailboxEnabled() {
1891c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        if (mCphsInfo == null)  return false;
1892c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return ((mCphsInfo[1] & CPHS_SST_MBN_MASK) == CPHS_SST_MBN_ENABLED );
1893c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1894c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1895cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
1896c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void log(String s) {
189799c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville        Rlog.d(LOG_TAG, "[SIMRecords] " + s);
1898c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1899c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1900cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
1901c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void loge(String s) {
190299c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville        Rlog.e(LOG_TAG, "[SIMRecords] " + s);
1903c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1904c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1905c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void logw(String s, Throwable tr) {
190699c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville        Rlog.w(LOG_TAG, "[SIMRecords] " + s, tr);
1907c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1908c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1909c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    protected void logv(String s) {
191099c2e1d6749cfad2a8ca94a47857d8c3bfc09454Wink Saville        Rlog.v(LOG_TAG, "[SIMRecords] " + s);
1911c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1912c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1913c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1914c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Return true if "Restriction of menu options for manual PLMN selection"
1915c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * bit is set or EF_CSP data is unavailable, return false otherwise.
1916c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1917cbaa45bbf2cab852b6c9c3a887e9f803d4e857eaWink Saville    @Override
1918c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    public boolean isCspPlmnEnabled() {
1919c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        return mCspPlmnEnabled;
1920c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
1921c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1922c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    /**
1923c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Parse EF_CSP data and check if
1924c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * "Restriction of menu options for manual PLMN selection" is
1925c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * Enabled/Disabled
1926c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     *
1927c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     * @param data EF_CSP hex data.
1928c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville     */
1929c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    private void handleEfCspData(byte[] data) {
1930c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // As per spec CPHS4_2.WW6, CPHS B.4.7.1, EF_CSP contains CPHS defined
1931c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // 18 bytes (i.e 9 service groups info) and additional data specific to
1932c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // operator. The valueAddedServicesGroup is not part of standard
1933c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // services. This is operator specific and can be programmed any where.
1934c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // Normally this is programmed as 10th service after the standard
1935c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        // services.
1936c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        int usedCspGroups = data.length / 2;
1937e17fb5a149610484b4bcda31cde04abfd4e5d4ecJake Hamby        // This is the "Service Group Number" of "Value Added Services Group".
1938c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        byte valueAddedServicesGroup = (byte)0xC0;
1939c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1940c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        mCspPlmnEnabled = true;
1941c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        for (int i = 0; i < usedCspGroups; i++) {
1942c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville             if (data[2 * i] == valueAddedServicesGroup) {
1943c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                 log("[CSP] found ValueAddedServicesGroup, value " + data[(2 * i) + 1]);
1944c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                 if ((data[(2 * i) + 1] & 0x80) == 0x80) {
1945c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     // Bit 8 is for
1946c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     // "Restriction of menu options for manual PLMN selection".
1947c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     // Operator Selection menu should be enabled.
1948c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     mCspPlmnEnabled = true;
1949c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                 } else {
1950c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     mCspPlmnEnabled = false;
1951c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     // Operator Selection menu should be disabled.
1952c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     // Operator Selection Mode should be set to Automatic.
1953c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     log("[CSP] Set Automatic Network Selection");
1954c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                     mNetworkSelectionModeAutomaticRegistrants.notifyRegistrants();
1955c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                 }
1956c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville                 return;
1957c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville             }
1958c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        }
1959c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville
1960c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville        log("[CSP] Value Added Service Group (0xC0), not found!");
1961c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville    }
196205ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka
196305ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka    @Override
196405ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
196505ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println("SIMRecords: " + this);
196605ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" extends:");
196705ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        super.dump(fd, pw, args);
196805ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mVmConfig=" + mVmConfig);
196905ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mSpnOverride=" + mSpnOverride);
197022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mCallForwardingEnabled=" + mCallForwardingEnabled);
197122d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mSpnState=" + mSpnState);
197205ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mCphsInfo=" + mCphsInfo);
197305ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mCspPlmnEnabled=" + mCspPlmnEnabled);
197422d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mEfMWIS[]=" + Arrays.toString(mEfMWIS));
197522d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mEfCPHS_MWI[]=" + Arrays.toString(mEfCPHS_MWI));
197605ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mEfCff[]=" + Arrays.toString(mEfCff));
197705ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mEfCfis[]=" + Arrays.toString(mEfCfis));
197822d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mSpnDisplayCondition=" + mSpnDisplayCondition);
197922d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mSpdiNetworks[]=" + mSpdiNetworks);
198022d85a8e3a575a6d01d2c788587971657dfe20c6Wink Saville        pw.println(" mPnnHomeName=" + mPnnHomeName);
198105ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.println(" mUsimServiceTable=" + mUsimServiceTable);
1982620c8855bcaa3fe8d492e93811b0ed6e8b4f59fcRobert Greenwalt        pw.println(" mGid1=" + mGid1);
19837234bd8664dbec97858f3f635eaa01c77d2f2881Junda Liu        pw.println(" mGid2=" + mGid2);
198405ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka        pw.flush();
198505ef3b65972826780859b9acbd1fa9580d099832Alex Yakavenka    }
1986c38bb60d867c5d61d90b7179a9ed2b2d1848124fWink Saville}
1987