1916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath/*
2916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * Copyright (C) 2011 The Android Open Source Project
3916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath *
4916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * Licensed under the Apache License, Version 2.0 (the "License");
5916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * you may not use this file except in compliance with the License.
6916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * You may obtain a copy of the License at
7916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath *
8916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath *      http://www.apache.org/licenses/LICENSE-2.0
9916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath *
10916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * Unless required by applicable law or agreed to in writing, software
11916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * distributed under the License is distributed on an "AS IS" BASIS,
12916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * See the License for the specific language governing permissions and
14916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * limitations under the License.
15916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath */
16916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
17916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamathpackage com.android.dex;
18916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
19916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamathimport com.android.dex.util.ByteInput;
20916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
21916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath/**
22916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath * Pull parser for encoded values.
23916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath */
24916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamathpublic final class EncodedValueReader {
25916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_BYTE = 0x00;
26916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_SHORT = 0x02;
27916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_CHAR = 0x03;
28916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_INT = 0x04;
29916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_LONG = 0x06;
30916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_FLOAT = 0x10;
31916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_DOUBLE = 0x11;
32ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    public static final int ENCODED_METHOD_TYPE = 0x15;
33ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    public static final int ENCODED_METHOD_HANDLE = 0x16;
34916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_STRING = 0x17;
35916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_TYPE = 0x18;
36916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_FIELD = 0x19;
37916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_ENUM = 0x1b;
38916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_METHOD = 0x1a;
39916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_ARRAY = 0x1c;
40916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_ANNOTATION = 0x1d;
41916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_NULL = 0x1e;
42916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public static final int ENCODED_BOOLEAN = 0x1f;
43916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
44916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /** placeholder type if the type is not yet known */
45916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    private static final int MUST_READ = -1;
46916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
47916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    protected final ByteInput in;
48916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    private int type = MUST_READ;
49916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    private int annotationType;
50916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    private int arg;
51916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
52916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public EncodedValueReader(ByteInput in) {
53916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        this.in = in;
54916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
55916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
56916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public EncodedValueReader(EncodedValue in) {
57916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        this(in.asByteInput());
58916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
59916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
60916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
61916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Creates a new encoded value reader whose only value is the specified
62916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * known type. This is useful for encoded values without a type prefix,
63916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * such as class_def_item's encoded_array or annotation_item's
64916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * encoded_annotation.
65916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
66916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public EncodedValueReader(ByteInput in, int knownType) {
67916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        this.in = in;
68916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        this.type = knownType;
69916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
70916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
71916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public EncodedValueReader(EncodedValue in, int knownType) {
72916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        this(in.asByteInput(), knownType);
73916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
74916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
75916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
76916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Returns the type of the next value to read.
77916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
78916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int peek() {
79916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        if (type == MUST_READ) {
80916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            int argAndType = in.readByte() & 0xff;
81916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            type = argAndType & 0x1f;
82916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            arg = (argAndType & 0xe0) >> 5;
83916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        }
84916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return type;
85916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
86916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
87916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
88916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Begins reading the elements of an array, returning the array's size. The
89916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * caller must follow up by calling a read method for each element in the
90916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * array. For example, this reads a byte array: <pre>   {@code
91916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   int arraySize = readArray();
92916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   for (int i = 0, i < arraySize; i++) {
93916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *     readByte();
94916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   }
95916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * }</pre>
96916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
97916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readArray() {
98916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_ARRAY);
99916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
100916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return Leb128.readUnsignedLeb128(in);
101916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
102916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
103916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
104916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Begins reading the fields of an annotation, returning the number of
105916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * fields. The caller must follow up by making alternating calls to {@link
106916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * #readAnnotationName()} and another read method. For example, this reads
107916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * an annotation whose fields are all bytes: <pre>   {@code
108916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   int fieldCount = readAnnotation();
109916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   int annotationType = getAnnotationType();
110916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   for (int i = 0; i < fieldCount; i++) {
111916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *       readAnnotationName();
112916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *       readByte();
113916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     *   }
114916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * }</pre>
115916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
116916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readAnnotation() {
117916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_ANNOTATION);
118916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
119916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        annotationType = Leb128.readUnsignedLeb128(in);
120916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return Leb128.readUnsignedLeb128(in);
121916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
122916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
123916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
124916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Returns the type of the annotation just returned by {@link
125916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * #readAnnotation()}. This method's value is undefined unless the most
126916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * recent call was to {@link #readAnnotation()}.
127916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
128916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int getAnnotationType() {
129916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return annotationType;
130916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
131916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
132916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readAnnotationName() {
133916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return Leb128.readUnsignedLeb128(in);
134916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
135916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
136916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public byte readByte() {
137916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_BYTE);
138916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
139916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return (byte) EncodedValueCodec.readSignedInt(in, arg);
140916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
141916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
142916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public short readShort() {
143916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_SHORT);
144916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
145916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return (short) EncodedValueCodec.readSignedInt(in, arg);
146916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
147916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
148916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public char readChar() {
149916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_CHAR);
150916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
151916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return (char) EncodedValueCodec.readUnsignedInt(in, arg, false);
152916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
153916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
154916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readInt() {
155916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_INT);
156916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
157916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readSignedInt(in, arg);
158916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
159916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
160916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public long readLong() {
161916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_LONG);
162916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
163916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readSignedLong(in, arg);
164916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
165916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
166916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public float readFloat() {
167916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_FLOAT);
168916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
169916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return Float.intBitsToFloat(EncodedValueCodec.readUnsignedInt(in, arg, true));
170916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
171916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
172916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public double readDouble() {
173916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_DOUBLE);
174916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
175916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return Double.longBitsToDouble(EncodedValueCodec.readUnsignedLong(in, arg, true));
176916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
177916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
178ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    public int readMethodType() {
179ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        checkType(ENCODED_METHOD_TYPE);
180ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        type = MUST_READ;
181ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        return EncodedValueCodec.readUnsignedInt(in, arg, false);
182ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    }
183ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon
184ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    public int readMethodHandle() {
185ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        checkType(ENCODED_METHOD_HANDLE);
186ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        type = MUST_READ;
187ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        return EncodedValueCodec.readUnsignedInt(in, arg, false);
188ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon    }
189ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon
190916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readString() {
191916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_STRING);
192916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
193916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readUnsignedInt(in, arg, false);
194916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
195916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
196916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readType() {
197916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_TYPE);
198916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
199916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readUnsignedInt(in, arg, false);
200916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
201916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
202916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readField() {
203916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_FIELD);
204916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
205916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readUnsignedInt(in, arg, false);
206916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
207916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
208916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readEnum() {
209916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_ENUM);
210916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
211916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readUnsignedInt(in, arg, false);
212916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
213916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
214916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public int readMethod() {
215916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_METHOD);
216916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
217916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return EncodedValueCodec.readUnsignedInt(in, arg, false);
218916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
219916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
220916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public void readNull() {
221916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_NULL);
222916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
223916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
224916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
225916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public boolean readBoolean() {
226916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        checkType(ENCODED_BOOLEAN);
227916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        type = MUST_READ;
228916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        return arg != 0;
229916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
230916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
231916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    /**
232916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * Skips a single value, including its nested values if it is an array or
233916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     * annotation.
234916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath     */
235916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    public void skipValue() {
236916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        switch (peek()) {
237916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_BYTE:
238916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readByte();
239916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
240916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_SHORT:
241916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readShort();
242916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
243916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_CHAR:
244916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readChar();
245916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
246916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_INT:
247916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readInt();
248916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
249916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_LONG:
250916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readLong();
251916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
252916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_FLOAT:
253916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readFloat();
254916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
255916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_DOUBLE:
256916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readDouble();
257916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
258ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        case ENCODED_METHOD_TYPE:
259ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon            readMethodType();
260ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon            break;
261ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon        case ENCODED_METHOD_HANDLE:
262ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon            readMethodHandle();
263ebf02b65aed5b5e5f9b1e1e9ab345fea82dc2341Liam Miller-Cushon            break;
264916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_STRING:
265916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readString();
266916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
267916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_TYPE:
268916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readType();
269916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
270916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_FIELD:
271916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readField();
272916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
273916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_ENUM:
274916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readEnum();
275916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
276916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_METHOD:
277916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readMethod();
278916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
279916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_ARRAY:
280916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            for (int i = 0, size = readArray(); i < size; i++) {
281916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath                skipValue();
282916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            }
283916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
284916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_ANNOTATION:
285916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            for (int i = 0, size = readAnnotation(); i < size; i++) {
286916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath                readAnnotationName();
287916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath                skipValue();
288916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            }
289916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
290916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_NULL:
291916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readNull();
292916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
293916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        case ENCODED_BOOLEAN:
294916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            readBoolean();
295916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            break;
296916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        default:
297916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            throw new DexException("Unexpected type: " + Integer.toHexString(type));
298916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        }
299916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
300916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath
301916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    private void checkType(int expected) {
302916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        if (peek() != expected) {
303916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath            throw new IllegalStateException(
304916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath                    String.format("Expected %x but was %x", expected, peek()));
305916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath        }
306916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath    }
307916c2feaf6fc24d63369cedb33ab815ec99d1bdfNarayan Kamath}
308