• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2006-2007 Google Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5  * use this file except in compliance with the License. You may obtain a copy of
6  * the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13  * License for the specific language governing permissions and limitations under
14  * the License.
15  */
16 
17 package com.android.internal.telephony.cat;
18 
19 import com.android.internal.telephony.GsmAlphabet;
20 import com.android.internal.telephony.cat.Duration.TimeUnit;
21 import com.android.internal.telephony.uicc.IccUtils;
22 
23 import android.annotation.UnsupportedAppUsage;
24 import android.content.res.Resources;
25 import android.content.res.Resources.NotFoundException;
26 import java.io.UnsupportedEncodingException;
27 import java.util.ArrayList;
28 import java.util.List;
29 
30 abstract class ValueParser {
31 
32     /**
33      * Search for a Command Details object from a list.
34      *
35      * @param ctlv List of ComprehensionTlv objects used for search
36      * @return An CtlvCommandDetails object found from the objects. If no
37      *         Command Details object is found, ResultException is thrown.
38      * @throws ResultException
39      */
retrieveCommandDetails(ComprehensionTlv ctlv)40     static CommandDetails retrieveCommandDetails(ComprehensionTlv ctlv)
41             throws ResultException {
42 
43         CommandDetails cmdDet = new CommandDetails();
44         byte[] rawValue = ctlv.getRawValue();
45         int valueIndex = ctlv.getValueIndex();
46         try {
47             cmdDet.compRequired = ctlv.isComprehensionRequired();
48             cmdDet.commandNumber = rawValue[valueIndex] & 0xff;
49             cmdDet.typeOfCommand = rawValue[valueIndex + 1] & 0xff;
50             cmdDet.commandQualifier = rawValue[valueIndex + 2] & 0xff;
51             return cmdDet;
52         } catch (IndexOutOfBoundsException e) {
53             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
54         }
55     }
56 
57     /**
58      * Search for a Device Identities object from a list.
59      *
60      * @param ctlv List of ComprehensionTlv objects used for search
61      * @return An CtlvDeviceIdentities object found from the objects. If no
62      *         Command Details object is found, ResultException is thrown.
63      * @throws ResultException
64      */
retrieveDeviceIdentities(ComprehensionTlv ctlv)65     static DeviceIdentities retrieveDeviceIdentities(ComprehensionTlv ctlv)
66             throws ResultException {
67 
68         DeviceIdentities devIds = new DeviceIdentities();
69         byte[] rawValue = ctlv.getRawValue();
70         int valueIndex = ctlv.getValueIndex();
71         try {
72             devIds.sourceId = rawValue[valueIndex] & 0xff;
73             devIds.destinationId = rawValue[valueIndex + 1] & 0xff;
74             return devIds;
75         } catch (IndexOutOfBoundsException e) {
76             throw new ResultException(ResultCode.REQUIRED_VALUES_MISSING);
77         }
78     }
79 
80     /**
81      * Retrieves Duration information from the Duration COMPREHENSION-TLV
82      * object.
83      *
84      * @param ctlv A Text Attribute COMPREHENSION-TLV object
85      * @return A Duration object
86      * @throws ResultException
87      */
retrieveDuration(ComprehensionTlv ctlv)88     static Duration retrieveDuration(ComprehensionTlv ctlv) throws ResultException {
89         int timeInterval = 0;
90         TimeUnit timeUnit = TimeUnit.SECOND;
91 
92         byte[] rawValue = ctlv.getRawValue();
93         int valueIndex = ctlv.getValueIndex();
94 
95         try {
96             timeUnit = TimeUnit.values()[(rawValue[valueIndex] & 0xff)];
97             timeInterval = rawValue[valueIndex + 1] & 0xff;
98         } catch (IndexOutOfBoundsException e) {
99             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
100         }
101         return new Duration(timeInterval, timeUnit);
102     }
103 
104     /**
105      * Retrieves Item information from the COMPREHENSION-TLV object.
106      *
107      * @param ctlv A Text Attribute COMPREHENSION-TLV object
108      * @return An Item
109      * @throws ResultException
110      */
retrieveItem(ComprehensionTlv ctlv)111     static Item retrieveItem(ComprehensionTlv ctlv) throws ResultException {
112         Item item = null;
113 
114         byte[] rawValue = ctlv.getRawValue();
115         int valueIndex = ctlv.getValueIndex();
116         int length = ctlv.getLength();
117 
118         if (length != 0) {
119             int textLen = length - 1;
120 
121             try {
122                 int id = rawValue[valueIndex] & 0xff;
123                 String text = IccUtils.adnStringFieldToString(rawValue,
124                         valueIndex + 1, textLen);
125                 item = new Item(id, text);
126             } catch (IndexOutOfBoundsException e) {
127                 throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
128             }
129         }
130 
131         return item;
132     }
133 
134     /**
135      * Retrieves Item id information from the COMPREHENSION-TLV object.
136      *
137      * @param ctlv A Text Attribute COMPREHENSION-TLV object
138      * @return An Item id
139      * @throws ResultException
140      */
retrieveItemId(ComprehensionTlv ctlv)141     static int retrieveItemId(ComprehensionTlv ctlv) throws ResultException {
142         int id = 0;
143 
144         byte[] rawValue = ctlv.getRawValue();
145         int valueIndex = ctlv.getValueIndex();
146 
147         try {
148             id = rawValue[valueIndex] & 0xff;
149         } catch (IndexOutOfBoundsException e) {
150             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
151         }
152 
153         return id;
154     }
155 
156     /**
157      * Retrieves icon id from an Icon Identifier COMPREHENSION-TLV object
158      *
159      * @param ctlv An Icon Identifier COMPREHENSION-TLV object
160      * @return IconId instance
161      * @throws ResultException
162      */
retrieveIconId(ComprehensionTlv ctlv)163     static IconId retrieveIconId(ComprehensionTlv ctlv) throws ResultException {
164         IconId id = new IconId();
165 
166         byte[] rawValue = ctlv.getRawValue();
167         int valueIndex = ctlv.getValueIndex();
168         try {
169             id.selfExplanatory = (rawValue[valueIndex++] & 0xff) == 0x00;
170             id.recordNumber = rawValue[valueIndex] & 0xff;
171         } catch (IndexOutOfBoundsException e) {
172             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
173         }
174 
175         return id;
176     }
177 
178     /**
179      * Retrieves item icons id from an Icon Identifier List COMPREHENSION-TLV
180      * object
181      *
182      * @param ctlv An Item Icon List Identifier COMPREHENSION-TLV object
183      * @return ItemsIconId instance
184      * @throws ResultException
185      */
retrieveItemsIconId(ComprehensionTlv ctlv)186     static ItemsIconId retrieveItemsIconId(ComprehensionTlv ctlv)
187             throws ResultException {
188         CatLog.d("ValueParser", "retrieveItemsIconId:");
189         ItemsIconId id = new ItemsIconId();
190 
191         byte[] rawValue = ctlv.getRawValue();
192         int valueIndex = ctlv.getValueIndex();
193         int numOfItems = ctlv.getLength() - 1;
194         id.recordNumbers = new int[numOfItems];
195 
196         try {
197             // get icon self-explanatory
198             id.selfExplanatory = (rawValue[valueIndex++] & 0xff) == 0x00;
199 
200             for (int index = 0; index < numOfItems;) {
201                 id.recordNumbers[index++] = rawValue[valueIndex++];
202             }
203         } catch (IndexOutOfBoundsException e) {
204             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
205         }
206         return id;
207     }
208 
209     /**
210      * Retrieves text attribute information from the Text Attribute
211      * COMPREHENSION-TLV object.
212      *
213      * @param ctlv A Text Attribute COMPREHENSION-TLV object
214      * @return A list of TextAttribute objects
215      * @throws ResultException
216      */
217     @UnsupportedAppUsage
retrieveTextAttribute(ComprehensionTlv ctlv)218     static List<TextAttribute> retrieveTextAttribute(ComprehensionTlv ctlv)
219             throws ResultException {
220         ArrayList<TextAttribute> lst = new ArrayList<TextAttribute>();
221 
222         byte[] rawValue = ctlv.getRawValue();
223         int valueIndex = ctlv.getValueIndex();
224         int length = ctlv.getLength();
225 
226         if (length != 0) {
227             // Each attribute is consisted of four bytes
228             int itemCount = length / 4;
229 
230             try {
231                 for (int i = 0; i < itemCount; i++, valueIndex += 4) {
232                     int start = rawValue[valueIndex] & 0xff;
233                     int textLength = rawValue[valueIndex + 1] & 0xff;
234                     int format = rawValue[valueIndex + 2] & 0xff;
235                     int colorValue = rawValue[valueIndex + 3] & 0xff;
236 
237                     int alignValue = format & 0x03;
238                     TextAlignment align = TextAlignment.fromInt(alignValue);
239 
240                     int sizeValue = (format >> 2) & 0x03;
241                     FontSize size = FontSize.fromInt(sizeValue);
242                     if (size == null) {
243                         // Font size value is not defined. Use default.
244                         size = FontSize.NORMAL;
245                     }
246 
247                     boolean bold = (format & 0x10) != 0;
248                     boolean italic = (format & 0x20) != 0;
249                     boolean underlined = (format & 0x40) != 0;
250                     boolean strikeThrough = (format & 0x80) != 0;
251 
252                     TextColor color = TextColor.fromInt(colorValue);
253 
254                     TextAttribute attr = new TextAttribute(start, textLength,
255                             align, size, bold, italic, underlined,
256                             strikeThrough, color);
257                     lst.add(attr);
258                 }
259 
260                 return lst;
261 
262             } catch (IndexOutOfBoundsException e) {
263                 throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
264             }
265         }
266         return null;
267     }
268 
269 
270     /**
271      * Retrieves alpha identifier from an Alpha Identifier COMPREHENSION-TLV
272      * object.
273      *
274      * @param ctlv An Alpha Identifier COMPREHENSION-TLV object
275      * @return String corresponding to the alpha identifier
276      * @throws ResultException
277      */
278     @UnsupportedAppUsage
retrieveAlphaId(ComprehensionTlv ctlv)279     static String retrieveAlphaId(ComprehensionTlv ctlv) throws ResultException {
280 
281         if (ctlv != null) {
282             byte[] rawValue = ctlv.getRawValue();
283             int valueIndex = ctlv.getValueIndex();
284             int length = ctlv.getLength();
285             if (length != 0) {
286                 try {
287                     return IccUtils.adnStringFieldToString(rawValue, valueIndex,
288                             length);
289                 } catch (IndexOutOfBoundsException e) {
290                     throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
291                 }
292             } else {
293                 CatLog.d("ValueParser", "Alpha Id length=" + length);
294                 return null;
295             }
296         } else {
297             /* Per 3GPP specification 102.223,
298              * if the alpha identifier is not provided by the UICC,
299              * the terminal MAY give information to the user
300              * noAlphaUsrCnf defines if you need to show user confirmation or not
301              */
302             boolean noAlphaUsrCnf = false;
303             Resources resource = Resources.getSystem();
304             try {
305                 noAlphaUsrCnf = resource.getBoolean(
306                         com.android.internal.R.bool.config_stkNoAlphaUsrCnf);
307             } catch (NotFoundException e) {
308                 noAlphaUsrCnf = false;
309             }
310             return (noAlphaUsrCnf ? null : CatService.STK_DEFAULT);
311         }
312     }
313 
314     /**
315      * Retrieves text from the Text COMPREHENSION-TLV object, and decodes it
316      * into a Java String.
317      *
318      * @param ctlv A Text COMPREHENSION-TLV object
319      * @return A Java String object decoded from the Text object
320      * @throws ResultException
321      */
322     @UnsupportedAppUsage
retrieveTextString(ComprehensionTlv ctlv)323     static String retrieveTextString(ComprehensionTlv ctlv) throws ResultException {
324         byte[] rawValue = ctlv.getRawValue();
325         int valueIndex = ctlv.getValueIndex();
326         byte codingScheme = 0x00;
327         String text = null;
328         int textLen = ctlv.getLength();
329 
330         // In case the text length is 0, return a null string.
331         if (textLen == 0) {
332             return text;
333         } else {
334             // one byte is coding scheme
335             textLen -= 1;
336         }
337 
338         try {
339             codingScheme = (byte) (rawValue[valueIndex] & 0x0c);
340 
341             if (codingScheme == 0x00) { // GSM 7-bit packed
342                 text = GsmAlphabet.gsm7BitPackedToString(rawValue,
343                         valueIndex + 1, (textLen * 8) / 7);
344             } else if (codingScheme == 0x04) { // GSM 8-bit unpacked
345                 text = GsmAlphabet.gsm8BitUnpackedToString(rawValue,
346                         valueIndex + 1, textLen);
347             } else if (codingScheme == 0x08) { // UCS2
348                 text = new String(rawValue, valueIndex + 1, textLen, "UTF-16");
349             } else {
350                 throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
351             }
352 
353             return text;
354         } catch (IndexOutOfBoundsException e) {
355             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
356         } catch (UnsupportedEncodingException e) {
357             // This should never happen.
358             throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
359         }
360     }
361 }
362