Parcel.java revision 4a7d824c3b41eafc4ff91d3253ff8a9ebd60a454
1/*
2 * Copyright (C) 2006 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.os;
18
19import android.text.TextUtils;
20import android.util.ArrayMap;
21import android.util.Log;
22import android.util.SparseArray;
23import android.util.SparseBooleanArray;
24
25import java.io.ByteArrayInputStream;
26import java.io.ByteArrayOutputStream;
27import java.io.FileDescriptor;
28import java.io.FileNotFoundException;
29import java.io.IOException;
30import java.io.ObjectInputStream;
31import java.io.ObjectOutputStream;
32import java.io.Serializable;
33import java.lang.reflect.Field;
34import java.util.ArrayList;
35import java.util.Arrays;
36import java.util.HashMap;
37import java.util.List;
38import java.util.Map;
39import java.util.Set;
40
41/**
42 * Container for a message (data and object references) that can
43 * be sent through an IBinder.  A Parcel can contain both flattened data
44 * that will be unflattened on the other side of the IPC (using the various
45 * methods here for writing specific types, or the general
46 * {@link Parcelable} interface), and references to live {@link IBinder}
47 * objects that will result in the other side receiving a proxy IBinder
48 * connected with the original IBinder in the Parcel.
49 *
50 * <p class="note">Parcel is <strong>not</strong> a general-purpose
51 * serialization mechanism.  This class (and the corresponding
52 * {@link Parcelable} API for placing arbitrary objects into a Parcel) is
53 * designed as a high-performance IPC transport.  As such, it is not
54 * appropriate to place any Parcel data in to persistent storage: changes
55 * in the underlying implementation of any of the data in the Parcel can
56 * render older data unreadable.</p>
57 *
58 * <p>The bulk of the Parcel API revolves around reading and writing data
59 * of various types.  There are six major classes of such functions available.</p>
60 *
61 * <h3>Primitives</h3>
62 *
63 * <p>The most basic data functions are for writing and reading primitive
64 * data types: {@link #writeByte}, {@link #readByte}, {@link #writeDouble},
65 * {@link #readDouble}, {@link #writeFloat}, {@link #readFloat}, {@link #writeInt},
66 * {@link #readInt}, {@link #writeLong}, {@link #readLong},
67 * {@link #writeString}, {@link #readString}.  Most other
68 * data operations are built on top of these.  The given data is written and
69 * read using the endianess of the host CPU.</p>
70 *
71 * <h3>Primitive Arrays</h3>
72 *
73 * <p>There are a variety of methods for reading and writing raw arrays
74 * of primitive objects, which generally result in writing a 4-byte length
75 * followed by the primitive data items.  The methods for reading can either
76 * read the data into an existing array, or create and return a new array.
77 * These available types are:</p>
78 *
79 * <ul>
80 * <li> {@link #writeBooleanArray(boolean[])},
81 * {@link #readBooleanArray(boolean[])}, {@link #createBooleanArray()}
82 * <li> {@link #writeByteArray(byte[])},
83 * {@link #writeByteArray(byte[], int, int)}, {@link #readByteArray(byte[])},
84 * {@link #createByteArray()}
85 * <li> {@link #writeCharArray(char[])}, {@link #readCharArray(char[])},
86 * {@link #createCharArray()}
87 * <li> {@link #writeDoubleArray(double[])}, {@link #readDoubleArray(double[])},
88 * {@link #createDoubleArray()}
89 * <li> {@link #writeFloatArray(float[])}, {@link #readFloatArray(float[])},
90 * {@link #createFloatArray()}
91 * <li> {@link #writeIntArray(int[])}, {@link #readIntArray(int[])},
92 * {@link #createIntArray()}
93 * <li> {@link #writeLongArray(long[])}, {@link #readLongArray(long[])},
94 * {@link #createLongArray()}
95 * <li> {@link #writeStringArray(String[])}, {@link #readStringArray(String[])},
96 * {@link #createStringArray()}.
97 * <li> {@link #writeSparseBooleanArray(SparseBooleanArray)},
98 * {@link #readSparseBooleanArray()}.
99 * </ul>
100 *
101 * <h3>Parcelables</h3>
102 *
103 * <p>The {@link Parcelable} protocol provides an extremely efficient (but
104 * low-level) protocol for objects to write and read themselves from Parcels.
105 * You can use the direct methods {@link #writeParcelable(Parcelable, int)}
106 * and {@link #readParcelable(ClassLoader)} or
107 * {@link #writeParcelableArray} and
108 * {@link #readParcelableArray(ClassLoader)} to write or read.  These
109 * methods write both the class type and its data to the Parcel, allowing
110 * that class to be reconstructed from the appropriate class loader when
111 * later reading.</p>
112 *
113 * <p>There are also some methods that provide a more efficient way to work
114 * with Parcelables: {@link #writeTypedArray},
115 * {@link #writeTypedList(List)},
116 * {@link #readTypedArray} and {@link #readTypedList}.  These methods
117 * do not write the class information of the original object: instead, the
118 * caller of the read function must know what type to expect and pass in the
119 * appropriate {@link Parcelable.Creator Parcelable.Creator} instead to
120 * properly construct the new object and read its data.  (To more efficient
121 * write and read a single Parceable object, you can directly call
122 * {@link Parcelable#writeToParcel Parcelable.writeToParcel} and
123 * {@link Parcelable.Creator#createFromParcel Parcelable.Creator.createFromParcel}
124 * yourself.)</p>
125 *
126 * <h3>Bundles</h3>
127 *
128 * <p>A special type-safe container, called {@link Bundle}, is available
129 * for key/value maps of heterogeneous values.  This has many optimizations
130 * for improved performance when reading and writing data, and its type-safe
131 * API avoids difficult to debug type errors when finally marshalling the
132 * data contents into a Parcel.  The methods to use are
133 * {@link #writeBundle(Bundle)}, {@link #readBundle()}, and
134 * {@link #readBundle(ClassLoader)}.
135 *
136 * <h3>Active Objects</h3>
137 *
138 * <p>An unusual feature of Parcel is the ability to read and write active
139 * objects.  For these objects the actual contents of the object is not
140 * written, rather a special token referencing the object is written.  When
141 * reading the object back from the Parcel, you do not get a new instance of
142 * the object, but rather a handle that operates on the exact same object that
143 * was originally written.  There are two forms of active objects available.</p>
144 *
145 * <p>{@link Binder} objects are a core facility of Android's general cross-process
146 * communication system.  The {@link IBinder} interface describes an abstract
147 * protocol with a Binder object.  Any such interface can be written in to
148 * a Parcel, and upon reading you will receive either the original object
149 * implementing that interface or a special proxy implementation
150 * that communicates calls back to the original object.  The methods to use are
151 * {@link #writeStrongBinder(IBinder)},
152 * {@link #writeStrongInterface(IInterface)}, {@link #readStrongBinder()},
153 * {@link #writeBinderArray(IBinder[])}, {@link #readBinderArray(IBinder[])},
154 * {@link #createBinderArray()},
155 * {@link #writeBinderList(List)}, {@link #readBinderList(List)},
156 * {@link #createBinderArrayList()}.</p>
157 *
158 * <p>FileDescriptor objects, representing raw Linux file descriptor identifiers,
159 * can be written and {@link ParcelFileDescriptor} objects returned to operate
160 * on the original file descriptor.  The returned file descriptor is a dup
161 * of the original file descriptor: the object and fd is different, but
162 * operating on the same underlying file stream, with the same position, etc.
163 * The methods to use are {@link #writeFileDescriptor(FileDescriptor)},
164 * {@link #readFileDescriptor()}.
165 *
166 * <h3>Untyped Containers</h3>
167 *
168 * <p>A final class of methods are for writing and reading standard Java
169 * containers of arbitrary types.  These all revolve around the
170 * {@link #writeValue(Object)} and {@link #readValue(ClassLoader)} methods
171 * which define the types of objects allowed.  The container methods are
172 * {@link #writeArray(Object[])}, {@link #readArray(ClassLoader)},
173 * {@link #writeList(List)}, {@link #readList(List, ClassLoader)},
174 * {@link #readArrayList(ClassLoader)},
175 * {@link #writeMap(Map)}, {@link #readMap(Map, ClassLoader)},
176 * {@link #writeSparseArray(SparseArray)},
177 * {@link #readSparseArray(ClassLoader)}.
178 */
179public final class Parcel {
180    private static final boolean DEBUG_RECYCLE = false;
181    private static final boolean DEBUG_ARRAY_MAP = false;
182    private static final String TAG = "Parcel";
183
184    @SuppressWarnings({"UnusedDeclaration"})
185    private int mNativePtr; // used by native code
186
187    /**
188     * Flag indicating if {@link #mNativePtr} was allocated by this object,
189     * indicating that we're responsible for its lifecycle.
190     */
191    private boolean mOwnsNativeParcelObject;
192
193    private RuntimeException mStack;
194
195    private static final int POOL_SIZE = 6;
196    private static final Parcel[] sOwnedPool = new Parcel[POOL_SIZE];
197    private static final Parcel[] sHolderPool = new Parcel[POOL_SIZE];
198
199    private static final int VAL_NULL = -1;
200    private static final int VAL_STRING = 0;
201    private static final int VAL_INTEGER = 1;
202    private static final int VAL_MAP = 2;
203    private static final int VAL_BUNDLE = 3;
204    private static final int VAL_PARCELABLE = 4;
205    private static final int VAL_SHORT = 5;
206    private static final int VAL_LONG = 6;
207    private static final int VAL_FLOAT = 7;
208    private static final int VAL_DOUBLE = 8;
209    private static final int VAL_BOOLEAN = 9;
210    private static final int VAL_CHARSEQUENCE = 10;
211    private static final int VAL_LIST  = 11;
212    private static final int VAL_SPARSEARRAY = 12;
213    private static final int VAL_BYTEARRAY = 13;
214    private static final int VAL_STRINGARRAY = 14;
215    private static final int VAL_IBINDER = 15;
216    private static final int VAL_PARCELABLEARRAY = 16;
217    private static final int VAL_OBJECTARRAY = 17;
218    private static final int VAL_INTARRAY = 18;
219    private static final int VAL_LONGARRAY = 19;
220    private static final int VAL_BYTE = 20;
221    private static final int VAL_SERIALIZABLE = 21;
222    private static final int VAL_SPARSEBOOLEANARRAY = 22;
223    private static final int VAL_BOOLEANARRAY = 23;
224    private static final int VAL_CHARSEQUENCEARRAY = 24;
225
226    // The initial int32 in a Binder call's reply Parcel header:
227    private static final int EX_SECURITY = -1;
228    private static final int EX_BAD_PARCELABLE = -2;
229    private static final int EX_ILLEGAL_ARGUMENT = -3;
230    private static final int EX_NULL_POINTER = -4;
231    private static final int EX_ILLEGAL_STATE = -5;
232    private static final int EX_NETWORK_MAIN_THREAD = -6;
233    private static final int EX_HAS_REPLY_HEADER = -128;  // special; see below
234
235    private static native int nativeDataSize(int nativePtr);
236    private static native int nativeDataAvail(int nativePtr);
237    private static native int nativeDataPosition(int nativePtr);
238    private static native int nativeDataCapacity(int nativePtr);
239    private static native void nativeSetDataSize(int nativePtr, int size);
240    private static native void nativeSetDataPosition(int nativePtr, int pos);
241    private static native void nativeSetDataCapacity(int nativePtr, int size);
242
243    private static native boolean nativePushAllowFds(int nativePtr, boolean allowFds);
244    private static native void nativeRestoreAllowFds(int nativePtr, boolean lastValue);
245
246    private static native void nativeWriteByteArray(int nativePtr, byte[] b, int offset, int len);
247    private static native void nativeWriteInt(int nativePtr, int val);
248    private static native void nativeWriteLong(int nativePtr, long val);
249    private static native void nativeWriteFloat(int nativePtr, float val);
250    private static native void nativeWriteDouble(int nativePtr, double val);
251    private static native void nativeWriteString(int nativePtr, String val);
252    private static native void nativeWriteStrongBinder(int nativePtr, IBinder val);
253    private static native void nativeWriteFileDescriptor(int nativePtr, FileDescriptor val);
254
255    private static native byte[] nativeCreateByteArray(int nativePtr);
256    private static native int nativeReadInt(int nativePtr);
257    private static native long nativeReadLong(int nativePtr);
258    private static native float nativeReadFloat(int nativePtr);
259    private static native double nativeReadDouble(int nativePtr);
260    private static native String nativeReadString(int nativePtr);
261    private static native IBinder nativeReadStrongBinder(int nativePtr);
262    private static native FileDescriptor nativeReadFileDescriptor(int nativePtr);
263
264    private static native int nativeCreate();
265    private static native void nativeFreeBuffer(int nativePtr);
266    private static native void nativeDestroy(int nativePtr);
267
268    private static native byte[] nativeMarshall(int nativePtr);
269    private static native void nativeUnmarshall(
270            int nativePtr, byte[] data, int offest, int length);
271    private static native void nativeAppendFrom(
272            int thisNativePtr, int otherNativePtr, int offset, int length);
273    private static native boolean nativeHasFileDescriptors(int nativePtr);
274    private static native void nativeWriteInterfaceToken(int nativePtr, String interfaceName);
275    private static native void nativeEnforceInterface(int nativePtr, String interfaceName);
276
277    public final static Parcelable.Creator<String> STRING_CREATOR
278             = new Parcelable.Creator<String>() {
279        public String createFromParcel(Parcel source) {
280            return source.readString();
281        }
282        public String[] newArray(int size) {
283            return new String[size];
284        }
285    };
286
287    /**
288     * Retrieve a new Parcel object from the pool.
289     */
290    public static Parcel obtain() {
291        final Parcel[] pool = sOwnedPool;
292        synchronized (pool) {
293            Parcel p;
294            for (int i=0; i<POOL_SIZE; i++) {
295                p = pool[i];
296                if (p != null) {
297                    pool[i] = null;
298                    if (DEBUG_RECYCLE) {
299                        p.mStack = new RuntimeException();
300                    }
301                    return p;
302                }
303            }
304        }
305        return new Parcel(0);
306    }
307
308    /**
309     * Put a Parcel object back into the pool.  You must not touch
310     * the object after this call.
311     */
312    public final void recycle() {
313        if (DEBUG_RECYCLE) mStack = null;
314        freeBuffer();
315
316        final Parcel[] pool;
317        if (mOwnsNativeParcelObject) {
318            pool = sOwnedPool;
319        } else {
320            mNativePtr = 0;
321            pool = sHolderPool;
322        }
323
324        synchronized (pool) {
325            for (int i=0; i<POOL_SIZE; i++) {
326                if (pool[i] == null) {
327                    pool[i] = this;
328                    return;
329                }
330            }
331        }
332    }
333
334    /**
335     * Returns the total amount of data contained in the parcel.
336     */
337    public final int dataSize() {
338        return nativeDataSize(mNativePtr);
339    }
340
341    /**
342     * Returns the amount of data remaining to be read from the
343     * parcel.  That is, {@link #dataSize}-{@link #dataPosition}.
344     */
345    public final int dataAvail() {
346        return nativeDataAvail(mNativePtr);
347    }
348
349    /**
350     * Returns the current position in the parcel data.  Never
351     * more than {@link #dataSize}.
352     */
353    public final int dataPosition() {
354        return nativeDataPosition(mNativePtr);
355    }
356
357    /**
358     * Returns the total amount of space in the parcel.  This is always
359     * >= {@link #dataSize}.  The difference between it and dataSize() is the
360     * amount of room left until the parcel needs to re-allocate its
361     * data buffer.
362     */
363    public final int dataCapacity() {
364        return nativeDataCapacity(mNativePtr);
365    }
366
367    /**
368     * Change the amount of data in the parcel.  Can be either smaller or
369     * larger than the current size.  If larger than the current capacity,
370     * more memory will be allocated.
371     *
372     * @param size The new number of bytes in the Parcel.
373     */
374    public final void setDataSize(int size) {
375        nativeSetDataSize(mNativePtr, size);
376    }
377
378    /**
379     * Move the current read/write position in the parcel.
380     * @param pos New offset in the parcel; must be between 0 and
381     * {@link #dataSize}.
382     */
383    public final void setDataPosition(int pos) {
384        nativeSetDataPosition(mNativePtr, pos);
385    }
386
387    /**
388     * Change the capacity (current available space) of the parcel.
389     *
390     * @param size The new capacity of the parcel, in bytes.  Can not be
391     * less than {@link #dataSize} -- that is, you can not drop existing data
392     * with this method.
393     */
394    public final void setDataCapacity(int size) {
395        nativeSetDataCapacity(mNativePtr, size);
396    }
397
398    /** @hide */
399    public final boolean pushAllowFds(boolean allowFds) {
400        return nativePushAllowFds(mNativePtr, allowFds);
401    }
402
403    /** @hide */
404    public final void restoreAllowFds(boolean lastValue) {
405        nativeRestoreAllowFds(mNativePtr, lastValue);
406    }
407
408    /**
409     * Returns the raw bytes of the parcel.
410     *
411     * <p class="note">The data you retrieve here <strong>must not</strong>
412     * be placed in any kind of persistent storage (on local disk, across
413     * a network, etc).  For that, you should use standard serialization
414     * or another kind of general serialization mechanism.  The Parcel
415     * marshalled representation is highly optimized for local IPC, and as
416     * such does not attempt to maintain compatibility with data created
417     * in different versions of the platform.
418     */
419    public final byte[] marshall() {
420        return nativeMarshall(mNativePtr);
421    }
422
423    /**
424     * Set the bytes in data to be the raw bytes of this Parcel.
425     */
426    public final void unmarshall(byte[] data, int offest, int length) {
427        nativeUnmarshall(mNativePtr, data, offest, length);
428    }
429
430    public final void appendFrom(Parcel parcel, int offset, int length) {
431        nativeAppendFrom(mNativePtr, parcel.mNativePtr, offset, length);
432    }
433
434    /**
435     * Report whether the parcel contains any marshalled file descriptors.
436     */
437    public final boolean hasFileDescriptors() {
438        return nativeHasFileDescriptors(mNativePtr);
439    }
440
441    /**
442     * Store or read an IBinder interface token in the parcel at the current
443     * {@link #dataPosition}.  This is used to validate that the marshalled
444     * transaction is intended for the target interface.
445     */
446    public final void writeInterfaceToken(String interfaceName) {
447        nativeWriteInterfaceToken(mNativePtr, interfaceName);
448    }
449
450    public final void enforceInterface(String interfaceName) {
451        nativeEnforceInterface(mNativePtr, interfaceName);
452    }
453
454    /**
455     * Write a byte array into the parcel at the current {@link #dataPosition},
456     * growing {@link #dataCapacity} if needed.
457     * @param b Bytes to place into the parcel.
458     */
459    public final void writeByteArray(byte[] b) {
460        writeByteArray(b, 0, (b != null) ? b.length : 0);
461    }
462
463    /**
464     * Write a byte array into the parcel at the current {@link #dataPosition},
465     * growing {@link #dataCapacity} if needed.
466     * @param b Bytes to place into the parcel.
467     * @param offset Index of first byte to be written.
468     * @param len Number of bytes to write.
469     */
470    public final void writeByteArray(byte[] b, int offset, int len) {
471        if (b == null) {
472            writeInt(-1);
473            return;
474        }
475        Arrays.checkOffsetAndCount(b.length, offset, len);
476        nativeWriteByteArray(mNativePtr, b, offset, len);
477    }
478
479    /**
480     * Write an integer value into the parcel at the current dataPosition(),
481     * growing dataCapacity() if needed.
482     */
483    public final void writeInt(int val) {
484        nativeWriteInt(mNativePtr, val);
485    }
486
487    /**
488     * Write a long integer value into the parcel at the current dataPosition(),
489     * growing dataCapacity() if needed.
490     */
491    public final void writeLong(long val) {
492        nativeWriteLong(mNativePtr, val);
493    }
494
495    /**
496     * Write a floating point value into the parcel at the current
497     * dataPosition(), growing dataCapacity() if needed.
498     */
499    public final void writeFloat(float val) {
500        nativeWriteFloat(mNativePtr, val);
501    }
502
503    /**
504     * Write a double precision floating point value into the parcel at the
505     * current dataPosition(), growing dataCapacity() if needed.
506     */
507    public final void writeDouble(double val) {
508        nativeWriteDouble(mNativePtr, val);
509    }
510
511    /**
512     * Write a string value into the parcel at the current dataPosition(),
513     * growing dataCapacity() if needed.
514     */
515    public final void writeString(String val) {
516        nativeWriteString(mNativePtr, val);
517    }
518
519    /**
520     * Write a CharSequence value into the parcel at the current dataPosition(),
521     * growing dataCapacity() if needed.
522     * @hide
523     */
524    public final void writeCharSequence(CharSequence val) {
525        TextUtils.writeToParcel(val, this, 0);
526    }
527
528    /**
529     * Write an object into the parcel at the current dataPosition(),
530     * growing dataCapacity() if needed.
531     */
532    public final void writeStrongBinder(IBinder val) {
533        nativeWriteStrongBinder(mNativePtr, val);
534    }
535
536    /**
537     * Write an object into the parcel at the current dataPosition(),
538     * growing dataCapacity() if needed.
539     */
540    public final void writeStrongInterface(IInterface val) {
541        writeStrongBinder(val == null ? null : val.asBinder());
542    }
543
544    /**
545     * Write a FileDescriptor into the parcel at the current dataPosition(),
546     * growing dataCapacity() if needed.
547     *
548     * <p class="caution">The file descriptor will not be closed, which may
549     * result in file descriptor leaks when objects are returned from Binder
550     * calls.  Use {@link ParcelFileDescriptor#writeToParcel} instead, which
551     * accepts contextual flags and will close the original file descriptor
552     * if {@link Parcelable#PARCELABLE_WRITE_RETURN_VALUE} is set.</p>
553     */
554    public final void writeFileDescriptor(FileDescriptor val) {
555        nativeWriteFileDescriptor(mNativePtr, val);
556    }
557
558    /**
559     * Write a byte value into the parcel at the current dataPosition(),
560     * growing dataCapacity() if needed.
561     */
562    public final void writeByte(byte val) {
563        writeInt(val);
564    }
565
566    /**
567     * Please use {@link #writeBundle} instead.  Flattens a Map into the parcel
568     * at the current dataPosition(),
569     * growing dataCapacity() if needed.  The Map keys must be String objects.
570     * The Map values are written using {@link #writeValue} and must follow
571     * the specification there.
572     *
573     * <p>It is strongly recommended to use {@link #writeBundle} instead of
574     * this method, since the Bundle class provides a type-safe API that
575     * allows you to avoid mysterious type errors at the point of marshalling.
576     */
577    public final void writeMap(Map val) {
578        writeMapInternal((Map<String, Object>) val);
579    }
580
581    /**
582     * Flatten a Map into the parcel at the current dataPosition(),
583     * growing dataCapacity() if needed.  The Map keys must be String objects.
584     */
585    /* package */ void writeMapInternal(Map<String,Object> val) {
586        if (val == null) {
587            writeInt(-1);
588            return;
589        }
590        Set<Map.Entry<String,Object>> entries = val.entrySet();
591        writeInt(entries.size());
592        for (Map.Entry<String,Object> e : entries) {
593            writeValue(e.getKey());
594            writeValue(e.getValue());
595        }
596    }
597
598    /**
599     * Flatten an ArrayMap into the parcel at the current dataPosition(),
600     * growing dataCapacity() if needed.  The Map keys must be String objects.
601     */
602    /* package */ void writeArrayMapInternal(ArrayMap<String,Object> val) {
603        if (val == null) {
604            writeInt(-1);
605            return;
606        }
607        final int N = val.size();
608        writeInt(N);
609        if (DEBUG_ARRAY_MAP) {
610            RuntimeException here =  new RuntimeException("here");
611            here.fillInStackTrace();
612            Log.d(TAG, "Writing " + N + " ArrayMap entries", here);
613        }
614        for (int i=0; i<N; i++) {
615            if (DEBUG_ARRAY_MAP) Log.d(TAG, "  Write #" + i + ": key=0x"
616                    + (val.keyAt(i) != null ? val.keyAt(i).hashCode() : 0) + " " + val.keyAt(i));
617            writeValue(val.keyAt(i));
618            writeValue(val.valueAt(i));
619        }
620    }
621
622    /**
623     * Flatten a Bundle into the parcel at the current dataPosition(),
624     * growing dataCapacity() if needed.
625     */
626    public final void writeBundle(Bundle val) {
627        if (val == null) {
628            writeInt(-1);
629            return;
630        }
631
632        val.writeToParcel(this, 0);
633    }
634
635    /**
636     * Flatten a List into the parcel at the current dataPosition(), growing
637     * dataCapacity() if needed.  The List values are written using
638     * {@link #writeValue} and must follow the specification there.
639     */
640    public final void writeList(List val) {
641        if (val == null) {
642            writeInt(-1);
643            return;
644        }
645        int N = val.size();
646        int i=0;
647        writeInt(N);
648        while (i < N) {
649            writeValue(val.get(i));
650            i++;
651        }
652    }
653
654    /**
655     * Flatten an Object array into the parcel at the current dataPosition(),
656     * growing dataCapacity() if needed.  The array values are written using
657     * {@link #writeValue} and must follow the specification there.
658     */
659    public final void writeArray(Object[] val) {
660        if (val == null) {
661            writeInt(-1);
662            return;
663        }
664        int N = val.length;
665        int i=0;
666        writeInt(N);
667        while (i < N) {
668            writeValue(val[i]);
669            i++;
670        }
671    }
672
673    /**
674     * Flatten a generic SparseArray into the parcel at the current
675     * dataPosition(), growing dataCapacity() if needed.  The SparseArray
676     * values are written using {@link #writeValue} and must follow the
677     * specification there.
678     */
679    public final void writeSparseArray(SparseArray<Object> val) {
680        if (val == null) {
681            writeInt(-1);
682            return;
683        }
684        int N = val.size();
685        writeInt(N);
686        int i=0;
687        while (i < N) {
688            writeInt(val.keyAt(i));
689            writeValue(val.valueAt(i));
690            i++;
691        }
692    }
693
694    public final void writeSparseBooleanArray(SparseBooleanArray val) {
695        if (val == null) {
696            writeInt(-1);
697            return;
698        }
699        int N = val.size();
700        writeInt(N);
701        int i=0;
702        while (i < N) {
703            writeInt(val.keyAt(i));
704            writeByte((byte)(val.valueAt(i) ? 1 : 0));
705            i++;
706        }
707    }
708
709    public final void writeBooleanArray(boolean[] val) {
710        if (val != null) {
711            int N = val.length;
712            writeInt(N);
713            for (int i=0; i<N; i++) {
714                writeInt(val[i] ? 1 : 0);
715            }
716        } else {
717            writeInt(-1);
718        }
719    }
720
721    public final boolean[] createBooleanArray() {
722        int N = readInt();
723        // >>2 as a fast divide-by-4 works in the create*Array() functions
724        // because dataAvail() will never return a negative number.  4 is
725        // the size of a stored boolean in the stream.
726        if (N >= 0 && N <= (dataAvail() >> 2)) {
727            boolean[] val = new boolean[N];
728            for (int i=0; i<N; i++) {
729                val[i] = readInt() != 0;
730            }
731            return val;
732        } else {
733            return null;
734        }
735    }
736
737    public final void readBooleanArray(boolean[] val) {
738        int N = readInt();
739        if (N == val.length) {
740            for (int i=0; i<N; i++) {
741                val[i] = readInt() != 0;
742            }
743        } else {
744            throw new RuntimeException("bad array lengths");
745        }
746    }
747
748    public final void writeCharArray(char[] val) {
749        if (val != null) {
750            int N = val.length;
751            writeInt(N);
752            for (int i=0; i<N; i++) {
753                writeInt((int)val[i]);
754            }
755        } else {
756            writeInt(-1);
757        }
758    }
759
760    public final char[] createCharArray() {
761        int N = readInt();
762        if (N >= 0 && N <= (dataAvail() >> 2)) {
763            char[] val = new char[N];
764            for (int i=0; i<N; i++) {
765                val[i] = (char)readInt();
766            }
767            return val;
768        } else {
769            return null;
770        }
771    }
772
773    public final void readCharArray(char[] val) {
774        int N = readInt();
775        if (N == val.length) {
776            for (int i=0; i<N; i++) {
777                val[i] = (char)readInt();
778            }
779        } else {
780            throw new RuntimeException("bad array lengths");
781        }
782    }
783
784    public final void writeIntArray(int[] val) {
785        if (val != null) {
786            int N = val.length;
787            writeInt(N);
788            for (int i=0; i<N; i++) {
789                writeInt(val[i]);
790            }
791        } else {
792            writeInt(-1);
793        }
794    }
795
796    public final int[] createIntArray() {
797        int N = readInt();
798        if (N >= 0 && N <= (dataAvail() >> 2)) {
799            int[] val = new int[N];
800            for (int i=0; i<N; i++) {
801                val[i] = readInt();
802            }
803            return val;
804        } else {
805            return null;
806        }
807    }
808
809    public final void readIntArray(int[] val) {
810        int N = readInt();
811        if (N == val.length) {
812            for (int i=0; i<N; i++) {
813                val[i] = readInt();
814            }
815        } else {
816            throw new RuntimeException("bad array lengths");
817        }
818    }
819
820    public final void writeLongArray(long[] val) {
821        if (val != null) {
822            int N = val.length;
823            writeInt(N);
824            for (int i=0; i<N; i++) {
825                writeLong(val[i]);
826            }
827        } else {
828            writeInt(-1);
829        }
830    }
831
832    public final long[] createLongArray() {
833        int N = readInt();
834        // >>3 because stored longs are 64 bits
835        if (N >= 0 && N <= (dataAvail() >> 3)) {
836            long[] val = new long[N];
837            for (int i=0; i<N; i++) {
838                val[i] = readLong();
839            }
840            return val;
841        } else {
842            return null;
843        }
844    }
845
846    public final void readLongArray(long[] val) {
847        int N = readInt();
848        if (N == val.length) {
849            for (int i=0; i<N; i++) {
850                val[i] = readLong();
851            }
852        } else {
853            throw new RuntimeException("bad array lengths");
854        }
855    }
856
857    public final void writeFloatArray(float[] val) {
858        if (val != null) {
859            int N = val.length;
860            writeInt(N);
861            for (int i=0; i<N; i++) {
862                writeFloat(val[i]);
863            }
864        } else {
865            writeInt(-1);
866        }
867    }
868
869    public final float[] createFloatArray() {
870        int N = readInt();
871        // >>2 because stored floats are 4 bytes
872        if (N >= 0 && N <= (dataAvail() >> 2)) {
873            float[] val = new float[N];
874            for (int i=0; i<N; i++) {
875                val[i] = readFloat();
876            }
877            return val;
878        } else {
879            return null;
880        }
881    }
882
883    public final void readFloatArray(float[] val) {
884        int N = readInt();
885        if (N == val.length) {
886            for (int i=0; i<N; i++) {
887                val[i] = readFloat();
888            }
889        } else {
890            throw new RuntimeException("bad array lengths");
891        }
892    }
893
894    public final void writeDoubleArray(double[] val) {
895        if (val != null) {
896            int N = val.length;
897            writeInt(N);
898            for (int i=0; i<N; i++) {
899                writeDouble(val[i]);
900            }
901        } else {
902            writeInt(-1);
903        }
904    }
905
906    public final double[] createDoubleArray() {
907        int N = readInt();
908        // >>3 because stored doubles are 8 bytes
909        if (N >= 0 && N <= (dataAvail() >> 3)) {
910            double[] val = new double[N];
911            for (int i=0; i<N; i++) {
912                val[i] = readDouble();
913            }
914            return val;
915        } else {
916            return null;
917        }
918    }
919
920    public final void readDoubleArray(double[] val) {
921        int N = readInt();
922        if (N == val.length) {
923            for (int i=0; i<N; i++) {
924                val[i] = readDouble();
925            }
926        } else {
927            throw new RuntimeException("bad array lengths");
928        }
929    }
930
931    public final void writeStringArray(String[] val) {
932        if (val != null) {
933            int N = val.length;
934            writeInt(N);
935            for (int i=0; i<N; i++) {
936                writeString(val[i]);
937            }
938        } else {
939            writeInt(-1);
940        }
941    }
942
943    public final String[] createStringArray() {
944        int N = readInt();
945        if (N >= 0) {
946            String[] val = new String[N];
947            for (int i=0; i<N; i++) {
948                val[i] = readString();
949            }
950            return val;
951        } else {
952            return null;
953        }
954    }
955
956    public final void readStringArray(String[] val) {
957        int N = readInt();
958        if (N == val.length) {
959            for (int i=0; i<N; i++) {
960                val[i] = readString();
961            }
962        } else {
963            throw new RuntimeException("bad array lengths");
964        }
965    }
966
967    public final void writeBinderArray(IBinder[] val) {
968        if (val != null) {
969            int N = val.length;
970            writeInt(N);
971            for (int i=0; i<N; i++) {
972                writeStrongBinder(val[i]);
973            }
974        } else {
975            writeInt(-1);
976        }
977    }
978
979    /**
980     * @hide
981     */
982    public final void writeCharSequenceArray(CharSequence[] val) {
983        if (val != null) {
984            int N = val.length;
985            writeInt(N);
986            for (int i=0; i<N; i++) {
987                writeCharSequence(val[i]);
988            }
989        } else {
990            writeInt(-1);
991        }
992    }
993
994    public final IBinder[] createBinderArray() {
995        int N = readInt();
996        if (N >= 0) {
997            IBinder[] val = new IBinder[N];
998            for (int i=0; i<N; i++) {
999                val[i] = readStrongBinder();
1000            }
1001            return val;
1002        } else {
1003            return null;
1004        }
1005    }
1006
1007    public final void readBinderArray(IBinder[] val) {
1008        int N = readInt();
1009        if (N == val.length) {
1010            for (int i=0; i<N; i++) {
1011                val[i] = readStrongBinder();
1012            }
1013        } else {
1014            throw new RuntimeException("bad array lengths");
1015        }
1016    }
1017
1018    /**
1019     * Flatten a List containing a particular object type into the parcel, at
1020     * the current dataPosition() and growing dataCapacity() if needed.  The
1021     * type of the objects in the list must be one that implements Parcelable.
1022     * Unlike the generic writeList() method, however, only the raw data of the
1023     * objects is written and not their type, so you must use the corresponding
1024     * readTypedList() to unmarshall them.
1025     *
1026     * @param val The list of objects to be written.
1027     *
1028     * @see #createTypedArrayList
1029     * @see #readTypedList
1030     * @see Parcelable
1031     */
1032    public final <T extends Parcelable> void writeTypedList(List<T> val) {
1033        if (val == null) {
1034            writeInt(-1);
1035            return;
1036        }
1037        int N = val.size();
1038        int i=0;
1039        writeInt(N);
1040        while (i < N) {
1041            T item = val.get(i);
1042            if (item != null) {
1043                writeInt(1);
1044                item.writeToParcel(this, 0);
1045            } else {
1046                writeInt(0);
1047            }
1048            i++;
1049        }
1050    }
1051
1052    /**
1053     * Flatten a List containing String objects into the parcel, at
1054     * the current dataPosition() and growing dataCapacity() if needed.  They
1055     * can later be retrieved with {@link #createStringArrayList} or
1056     * {@link #readStringList}.
1057     *
1058     * @param val The list of strings to be written.
1059     *
1060     * @see #createStringArrayList
1061     * @see #readStringList
1062     */
1063    public final void writeStringList(List<String> val) {
1064        if (val == null) {
1065            writeInt(-1);
1066            return;
1067        }
1068        int N = val.size();
1069        int i=0;
1070        writeInt(N);
1071        while (i < N) {
1072            writeString(val.get(i));
1073            i++;
1074        }
1075    }
1076
1077    /**
1078     * Flatten a List containing IBinder objects into the parcel, at
1079     * the current dataPosition() and growing dataCapacity() if needed.  They
1080     * can later be retrieved with {@link #createBinderArrayList} or
1081     * {@link #readBinderList}.
1082     *
1083     * @param val The list of strings to be written.
1084     *
1085     * @see #createBinderArrayList
1086     * @see #readBinderList
1087     */
1088    public final void writeBinderList(List<IBinder> val) {
1089        if (val == null) {
1090            writeInt(-1);
1091            return;
1092        }
1093        int N = val.size();
1094        int i=0;
1095        writeInt(N);
1096        while (i < N) {
1097            writeStrongBinder(val.get(i));
1098            i++;
1099        }
1100    }
1101
1102    /**
1103     * Flatten a heterogeneous array containing a particular object type into
1104     * the parcel, at
1105     * the current dataPosition() and growing dataCapacity() if needed.  The
1106     * type of the objects in the array must be one that implements Parcelable.
1107     * Unlike the {@link #writeParcelableArray} method, however, only the
1108     * raw data of the objects is written and not their type, so you must use
1109     * {@link #readTypedArray} with the correct corresponding
1110     * {@link Parcelable.Creator} implementation to unmarshall them.
1111     *
1112     * @param val The array of objects to be written.
1113     * @param parcelableFlags Contextual flags as per
1114     * {@link Parcelable#writeToParcel(Parcel, int) Parcelable.writeToParcel()}.
1115     *
1116     * @see #readTypedArray
1117     * @see #writeParcelableArray
1118     * @see Parcelable.Creator
1119     */
1120    public final <T extends Parcelable> void writeTypedArray(T[] val,
1121            int parcelableFlags) {
1122        if (val != null) {
1123            int N = val.length;
1124            writeInt(N);
1125            for (int i=0; i<N; i++) {
1126                T item = val[i];
1127                if (item != null) {
1128                    writeInt(1);
1129                    item.writeToParcel(this, parcelableFlags);
1130                } else {
1131                    writeInt(0);
1132                }
1133            }
1134        } else {
1135            writeInt(-1);
1136        }
1137    }
1138
1139    /**
1140     * Flatten a generic object in to a parcel.  The given Object value may
1141     * currently be one of the following types:
1142     *
1143     * <ul>
1144     * <li> null
1145     * <li> String
1146     * <li> Byte
1147     * <li> Short
1148     * <li> Integer
1149     * <li> Long
1150     * <li> Float
1151     * <li> Double
1152     * <li> Boolean
1153     * <li> String[]
1154     * <li> boolean[]
1155     * <li> byte[]
1156     * <li> int[]
1157     * <li> long[]
1158     * <li> Object[] (supporting objects of the same type defined here).
1159     * <li> {@link Bundle}
1160     * <li> Map (as supported by {@link #writeMap}).
1161     * <li> Any object that implements the {@link Parcelable} protocol.
1162     * <li> Parcelable[]
1163     * <li> CharSequence (as supported by {@link TextUtils#writeToParcel}).
1164     * <li> List (as supported by {@link #writeList}).
1165     * <li> {@link SparseArray} (as supported by {@link #writeSparseArray(SparseArray)}).
1166     * <li> {@link IBinder}
1167     * <li> Any object that implements Serializable (but see
1168     *      {@link #writeSerializable} for caveats).  Note that all of the
1169     *      previous types have relatively efficient implementations for
1170     *      writing to a Parcel; having to rely on the generic serialization
1171     *      approach is much less efficient and should be avoided whenever
1172     *      possible.
1173     * </ul>
1174     *
1175     * <p class="caution">{@link Parcelable} objects are written with
1176     * {@link Parcelable#writeToParcel} using contextual flags of 0.  When
1177     * serializing objects containing {@link ParcelFileDescriptor}s,
1178     * this may result in file descriptor leaks when they are returned from
1179     * Binder calls (where {@link Parcelable#PARCELABLE_WRITE_RETURN_VALUE}
1180     * should be used).</p>
1181     */
1182    public final void writeValue(Object v) {
1183        if (v == null) {
1184            writeInt(VAL_NULL);
1185        } else if (v instanceof String) {
1186            writeInt(VAL_STRING);
1187            writeString((String) v);
1188        } else if (v instanceof Integer) {
1189            writeInt(VAL_INTEGER);
1190            writeInt((Integer) v);
1191        } else if (v instanceof Map) {
1192            writeInt(VAL_MAP);
1193            writeMap((Map) v);
1194        } else if (v instanceof Bundle) {
1195            // Must be before Parcelable
1196            writeInt(VAL_BUNDLE);
1197            writeBundle((Bundle) v);
1198        } else if (v instanceof Parcelable) {
1199            writeInt(VAL_PARCELABLE);
1200            writeParcelable((Parcelable) v, 0);
1201        } else if (v instanceof Short) {
1202            writeInt(VAL_SHORT);
1203            writeInt(((Short) v).intValue());
1204        } else if (v instanceof Long) {
1205            writeInt(VAL_LONG);
1206            writeLong((Long) v);
1207        } else if (v instanceof Float) {
1208            writeInt(VAL_FLOAT);
1209            writeFloat((Float) v);
1210        } else if (v instanceof Double) {
1211            writeInt(VAL_DOUBLE);
1212            writeDouble((Double) v);
1213        } else if (v instanceof Boolean) {
1214            writeInt(VAL_BOOLEAN);
1215            writeInt((Boolean) v ? 1 : 0);
1216        } else if (v instanceof CharSequence) {
1217            // Must be after String
1218            writeInt(VAL_CHARSEQUENCE);
1219            writeCharSequence((CharSequence) v);
1220        } else if (v instanceof List) {
1221            writeInt(VAL_LIST);
1222            writeList((List) v);
1223        } else if (v instanceof SparseArray) {
1224            writeInt(VAL_SPARSEARRAY);
1225            writeSparseArray((SparseArray) v);
1226        } else if (v instanceof boolean[]) {
1227            writeInt(VAL_BOOLEANARRAY);
1228            writeBooleanArray((boolean[]) v);
1229        } else if (v instanceof byte[]) {
1230            writeInt(VAL_BYTEARRAY);
1231            writeByteArray((byte[]) v);
1232        } else if (v instanceof String[]) {
1233            writeInt(VAL_STRINGARRAY);
1234            writeStringArray((String[]) v);
1235        } else if (v instanceof CharSequence[]) {
1236            // Must be after String[] and before Object[]
1237            writeInt(VAL_CHARSEQUENCEARRAY);
1238            writeCharSequenceArray((CharSequence[]) v);
1239        } else if (v instanceof IBinder) {
1240            writeInt(VAL_IBINDER);
1241            writeStrongBinder((IBinder) v);
1242        } else if (v instanceof Parcelable[]) {
1243            writeInt(VAL_PARCELABLEARRAY);
1244            writeParcelableArray((Parcelable[]) v, 0);
1245        } else if (v instanceof Object[]) {
1246            writeInt(VAL_OBJECTARRAY);
1247            writeArray((Object[]) v);
1248        } else if (v instanceof int[]) {
1249            writeInt(VAL_INTARRAY);
1250            writeIntArray((int[]) v);
1251        } else if (v instanceof long[]) {
1252            writeInt(VAL_LONGARRAY);
1253            writeLongArray((long[]) v);
1254        } else if (v instanceof Byte) {
1255            writeInt(VAL_BYTE);
1256            writeInt((Byte) v);
1257        } else if (v instanceof Serializable) {
1258            // Must be last
1259            writeInt(VAL_SERIALIZABLE);
1260            writeSerializable((Serializable) v);
1261        } else {
1262            throw new RuntimeException("Parcel: unable to marshal value " + v);
1263        }
1264    }
1265
1266    /**
1267     * Flatten the name of the class of the Parcelable and its contents
1268     * into the parcel.
1269     *
1270     * @param p The Parcelable object to be written.
1271     * @param parcelableFlags Contextual flags as per
1272     * {@link Parcelable#writeToParcel(Parcel, int) Parcelable.writeToParcel()}.
1273     */
1274    public final void writeParcelable(Parcelable p, int parcelableFlags) {
1275        if (p == null) {
1276            writeString(null);
1277            return;
1278        }
1279        String name = p.getClass().getName();
1280        writeString(name);
1281        p.writeToParcel(this, parcelableFlags);
1282    }
1283
1284    /** @hide */
1285    public final void writeParcelableCreator(Parcelable p) {
1286        String name = p.getClass().getName();
1287        writeString(name);
1288    }
1289
1290    /**
1291     * Write a generic serializable object in to a Parcel.  It is strongly
1292     * recommended that this method be avoided, since the serialization
1293     * overhead is extremely large, and this approach will be much slower than
1294     * using the other approaches to writing data in to a Parcel.
1295     */
1296    public final void writeSerializable(Serializable s) {
1297        if (s == null) {
1298            writeString(null);
1299            return;
1300        }
1301        String name = s.getClass().getName();
1302        writeString(name);
1303
1304        ByteArrayOutputStream baos = new ByteArrayOutputStream();
1305        try {
1306            ObjectOutputStream oos = new ObjectOutputStream(baos);
1307            oos.writeObject(s);
1308            oos.close();
1309
1310            writeByteArray(baos.toByteArray());
1311        } catch (IOException ioe) {
1312            throw new RuntimeException("Parcelable encountered " +
1313                "IOException writing serializable object (name = " + name +
1314                ")", ioe);
1315        }
1316    }
1317
1318    /**
1319     * Special function for writing an exception result at the header of
1320     * a parcel, to be used when returning an exception from a transaction.
1321     * Note that this currently only supports a few exception types; any other
1322     * exception will be re-thrown by this function as a RuntimeException
1323     * (to be caught by the system's last-resort exception handling when
1324     * dispatching a transaction).
1325     *
1326     * <p>The supported exception types are:
1327     * <ul>
1328     * <li>{@link BadParcelableException}
1329     * <li>{@link IllegalArgumentException}
1330     * <li>{@link IllegalStateException}
1331     * <li>{@link NullPointerException}
1332     * <li>{@link SecurityException}
1333     * <li>{@link NetworkOnMainThreadException}
1334     * </ul>
1335     *
1336     * @param e The Exception to be written.
1337     *
1338     * @see #writeNoException
1339     * @see #readException
1340     */
1341    public final void writeException(Exception e) {
1342        int code = 0;
1343        if (e instanceof SecurityException) {
1344            code = EX_SECURITY;
1345        } else if (e instanceof BadParcelableException) {
1346            code = EX_BAD_PARCELABLE;
1347        } else if (e instanceof IllegalArgumentException) {
1348            code = EX_ILLEGAL_ARGUMENT;
1349        } else if (e instanceof NullPointerException) {
1350            code = EX_NULL_POINTER;
1351        } else if (e instanceof IllegalStateException) {
1352            code = EX_ILLEGAL_STATE;
1353        } else if (e instanceof NetworkOnMainThreadException) {
1354            code = EX_NETWORK_MAIN_THREAD;
1355        }
1356        writeInt(code);
1357        StrictMode.clearGatheredViolations();
1358        if (code == 0) {
1359            if (e instanceof RuntimeException) {
1360                throw (RuntimeException) e;
1361            }
1362            throw new RuntimeException(e);
1363        }
1364        writeString(e.getMessage());
1365    }
1366
1367    /**
1368     * Special function for writing information at the front of the Parcel
1369     * indicating that no exception occurred.
1370     *
1371     * @see #writeException
1372     * @see #readException
1373     */
1374    public final void writeNoException() {
1375        // Despite the name of this function ("write no exception"),
1376        // it should instead be thought of as "write the RPC response
1377        // header", but because this function name is written out by
1378        // the AIDL compiler, we're not going to rename it.
1379        //
1380        // The response header, in the non-exception case (see also
1381        // writeException above, also called by the AIDL compiler), is
1382        // either a 0 (the default case), or EX_HAS_REPLY_HEADER if
1383        // StrictMode has gathered up violations that have occurred
1384        // during a Binder call, in which case we write out the number
1385        // of violations and their details, serialized, before the
1386        // actual RPC respons data.  The receiving end of this is
1387        // readException(), below.
1388        if (StrictMode.hasGatheredViolations()) {
1389            writeInt(EX_HAS_REPLY_HEADER);
1390            final int sizePosition = dataPosition();
1391            writeInt(0);  // total size of fat header, to be filled in later
1392            StrictMode.writeGatheredViolationsToParcel(this);
1393            final int payloadPosition = dataPosition();
1394            setDataPosition(sizePosition);
1395            writeInt(payloadPosition - sizePosition);  // header size
1396            setDataPosition(payloadPosition);
1397        } else {
1398            writeInt(0);
1399        }
1400    }
1401
1402    /**
1403     * Special function for reading an exception result from the header of
1404     * a parcel, to be used after receiving the result of a transaction.  This
1405     * will throw the exception for you if it had been written to the Parcel,
1406     * otherwise return and let you read the normal result data from the Parcel.
1407     *
1408     * @see #writeException
1409     * @see #writeNoException
1410     */
1411    public final void readException() {
1412        int code = readExceptionCode();
1413        if (code != 0) {
1414            String msg = readString();
1415            readException(code, msg);
1416        }
1417    }
1418
1419    /**
1420     * Parses the header of a Binder call's response Parcel and
1421     * returns the exception code.  Deals with lite or fat headers.
1422     * In the common successful case, this header is generally zero.
1423     * In less common cases, it's a small negative number and will be
1424     * followed by an error string.
1425     *
1426     * This exists purely for android.database.DatabaseUtils and
1427     * insulating it from having to handle fat headers as returned by
1428     * e.g. StrictMode-induced RPC responses.
1429     *
1430     * @hide
1431     */
1432    public final int readExceptionCode() {
1433        int code = readInt();
1434        if (code == EX_HAS_REPLY_HEADER) {
1435            int headerSize = readInt();
1436            if (headerSize == 0) {
1437                Log.e(TAG, "Unexpected zero-sized Parcel reply header.");
1438            } else {
1439                // Currently the only thing in the header is StrictMode stacks,
1440                // but discussions around event/RPC tracing suggest we might
1441                // put that here too.  If so, switch on sub-header tags here.
1442                // But for now, just parse out the StrictMode stuff.
1443                StrictMode.readAndHandleBinderCallViolations(this);
1444            }
1445            // And fat response headers are currently only used when
1446            // there are no exceptions, so return no error:
1447            return 0;
1448        }
1449        return code;
1450    }
1451
1452    /**
1453     * Use this function for customized exception handling.
1454     * customized method call this method for all unknown case
1455     * @param code exception code
1456     * @param msg exception message
1457     */
1458    public final void readException(int code, String msg) {
1459        switch (code) {
1460            case EX_SECURITY:
1461                throw new SecurityException(msg);
1462            case EX_BAD_PARCELABLE:
1463                throw new BadParcelableException(msg);
1464            case EX_ILLEGAL_ARGUMENT:
1465                throw new IllegalArgumentException(msg);
1466            case EX_NULL_POINTER:
1467                throw new NullPointerException(msg);
1468            case EX_ILLEGAL_STATE:
1469                throw new IllegalStateException(msg);
1470            case EX_NETWORK_MAIN_THREAD:
1471                throw new NetworkOnMainThreadException();
1472        }
1473        throw new RuntimeException("Unknown exception code: " + code
1474                + " msg " + msg);
1475    }
1476
1477    /**
1478     * Read an integer value from the parcel at the current dataPosition().
1479     */
1480    public final int readInt() {
1481        return nativeReadInt(mNativePtr);
1482    }
1483
1484    /**
1485     * Read a long integer value from the parcel at the current dataPosition().
1486     */
1487    public final long readLong() {
1488        return nativeReadLong(mNativePtr);
1489    }
1490
1491    /**
1492     * Read a floating point value from the parcel at the current
1493     * dataPosition().
1494     */
1495    public final float readFloat() {
1496        return nativeReadFloat(mNativePtr);
1497    }
1498
1499    /**
1500     * Read a double precision floating point value from the parcel at the
1501     * current dataPosition().
1502     */
1503    public final double readDouble() {
1504        return nativeReadDouble(mNativePtr);
1505    }
1506
1507    /**
1508     * Read a string value from the parcel at the current dataPosition().
1509     */
1510    public final String readString() {
1511        return nativeReadString(mNativePtr);
1512    }
1513
1514    /**
1515     * Read a CharSequence value from the parcel at the current dataPosition().
1516     * @hide
1517     */
1518    public final CharSequence readCharSequence() {
1519        return TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(this);
1520    }
1521
1522    /**
1523     * Read an object from the parcel at the current dataPosition().
1524     */
1525    public final IBinder readStrongBinder() {
1526        return nativeReadStrongBinder(mNativePtr);
1527    }
1528
1529    /**
1530     * Read a FileDescriptor from the parcel at the current dataPosition().
1531     */
1532    public final ParcelFileDescriptor readFileDescriptor() {
1533        FileDescriptor fd = nativeReadFileDescriptor(mNativePtr);
1534        return fd != null ? new ParcelFileDescriptor(fd) : null;
1535    }
1536
1537    /** {@hide} */
1538    public final FileDescriptor readRawFileDescriptor() {
1539        return nativeReadFileDescriptor(mNativePtr);
1540    }
1541
1542    /*package*/ static native FileDescriptor openFileDescriptor(String file,
1543            int mode) throws FileNotFoundException;
1544    /*package*/ static native FileDescriptor dupFileDescriptor(FileDescriptor orig)
1545            throws IOException;
1546    /*package*/ static native void closeFileDescriptor(FileDescriptor desc)
1547            throws IOException;
1548    /*package*/ static native void clearFileDescriptor(FileDescriptor desc);
1549
1550    /**
1551     * Read a byte value from the parcel at the current dataPosition().
1552     */
1553    public final byte readByte() {
1554        return (byte)(readInt() & 0xff);
1555    }
1556
1557    /**
1558     * Please use {@link #readBundle(ClassLoader)} instead (whose data must have
1559     * been written with {@link #writeBundle}.  Read into an existing Map object
1560     * from the parcel at the current dataPosition().
1561     */
1562    public final void readMap(Map outVal, ClassLoader loader) {
1563        int N = readInt();
1564        readMapInternal(outVal, N, loader);
1565    }
1566
1567    /**
1568     * Read into an existing List object from the parcel at the current
1569     * dataPosition(), using the given class loader to load any enclosed
1570     * Parcelables.  If it is null, the default class loader is used.
1571     */
1572    public final void readList(List outVal, ClassLoader loader) {
1573        int N = readInt();
1574        readListInternal(outVal, N, loader);
1575    }
1576
1577    /**
1578     * Please use {@link #readBundle(ClassLoader)} instead (whose data must have
1579     * been written with {@link #writeBundle}.  Read and return a new HashMap
1580     * object from the parcel at the current dataPosition(), using the given
1581     * class loader to load any enclosed Parcelables.  Returns null if
1582     * the previously written map object was null.
1583     */
1584    public final HashMap readHashMap(ClassLoader loader)
1585    {
1586        int N = readInt();
1587        if (N < 0) {
1588            return null;
1589        }
1590        HashMap m = new HashMap(N);
1591        readMapInternal(m, N, loader);
1592        return m;
1593    }
1594
1595    /**
1596     * Read and return a new Bundle object from the parcel at the current
1597     * dataPosition().  Returns null if the previously written Bundle object was
1598     * null.
1599     */
1600    public final Bundle readBundle() {
1601        return readBundle(null);
1602    }
1603
1604    /**
1605     * Read and return a new Bundle object from the parcel at the current
1606     * dataPosition(), using the given class loader to initialize the class
1607     * loader of the Bundle for later retrieval of Parcelable objects.
1608     * Returns null if the previously written Bundle object was null.
1609     */
1610    public final Bundle readBundle(ClassLoader loader) {
1611        int length = readInt();
1612        if (length < 0) {
1613            if (Bundle.DEBUG) Log.d(TAG, "null bundle: length=" + length);
1614            return null;
1615        }
1616
1617        final Bundle bundle = new Bundle(this, length);
1618        if (loader != null) {
1619            bundle.setClassLoader(loader);
1620        }
1621        return bundle;
1622    }
1623
1624    /**
1625     * Read and return a byte[] object from the parcel.
1626     */
1627    public final byte[] createByteArray() {
1628        return nativeCreateByteArray(mNativePtr);
1629    }
1630
1631    /**
1632     * Read a byte[] object from the parcel and copy it into the
1633     * given byte array.
1634     */
1635    public final void readByteArray(byte[] val) {
1636        // TODO: make this a native method to avoid the extra copy.
1637        byte[] ba = createByteArray();
1638        if (ba.length == val.length) {
1639           System.arraycopy(ba, 0, val, 0, ba.length);
1640        } else {
1641            throw new RuntimeException("bad array lengths");
1642        }
1643    }
1644
1645    /**
1646     * Read and return a String[] object from the parcel.
1647     * {@hide}
1648     */
1649    public final String[] readStringArray() {
1650        String[] array = null;
1651
1652        int length = readInt();
1653        if (length >= 0)
1654        {
1655            array = new String[length];
1656
1657            for (int i = 0 ; i < length ; i++)
1658            {
1659                array[i] = readString();
1660            }
1661        }
1662
1663        return array;
1664    }
1665
1666    /**
1667     * Read and return a CharSequence[] object from the parcel.
1668     * {@hide}
1669     */
1670    public final CharSequence[] readCharSequenceArray() {
1671        CharSequence[] array = null;
1672
1673        int length = readInt();
1674        if (length >= 0)
1675        {
1676            array = new CharSequence[length];
1677
1678            for (int i = 0 ; i < length ; i++)
1679            {
1680                array[i] = readCharSequence();
1681            }
1682        }
1683
1684        return array;
1685    }
1686
1687    /**
1688     * Read and return a new ArrayList object from the parcel at the current
1689     * dataPosition().  Returns null if the previously written list object was
1690     * null.  The given class loader will be used to load any enclosed
1691     * Parcelables.
1692     */
1693    public final ArrayList readArrayList(ClassLoader loader) {
1694        int N = readInt();
1695        if (N < 0) {
1696            return null;
1697        }
1698        ArrayList l = new ArrayList(N);
1699        readListInternal(l, N, loader);
1700        return l;
1701    }
1702
1703    /**
1704     * Read and return a new Object array from the parcel at the current
1705     * dataPosition().  Returns null if the previously written array was
1706     * null.  The given class loader will be used to load any enclosed
1707     * Parcelables.
1708     */
1709    public final Object[] readArray(ClassLoader loader) {
1710        int N = readInt();
1711        if (N < 0) {
1712            return null;
1713        }
1714        Object[] l = new Object[N];
1715        readArrayInternal(l, N, loader);
1716        return l;
1717    }
1718
1719    /**
1720     * Read and return a new SparseArray object from the parcel at the current
1721     * dataPosition().  Returns null if the previously written list object was
1722     * null.  The given class loader will be used to load any enclosed
1723     * Parcelables.
1724     */
1725    public final SparseArray readSparseArray(ClassLoader loader) {
1726        int N = readInt();
1727        if (N < 0) {
1728            return null;
1729        }
1730        SparseArray sa = new SparseArray(N);
1731        readSparseArrayInternal(sa, N, loader);
1732        return sa;
1733    }
1734
1735    /**
1736     * Read and return a new SparseBooleanArray object from the parcel at the current
1737     * dataPosition().  Returns null if the previously written list object was
1738     * null.
1739     */
1740    public final SparseBooleanArray readSparseBooleanArray() {
1741        int N = readInt();
1742        if (N < 0) {
1743            return null;
1744        }
1745        SparseBooleanArray sa = new SparseBooleanArray(N);
1746        readSparseBooleanArrayInternal(sa, N);
1747        return sa;
1748    }
1749
1750    /**
1751     * Read and return a new ArrayList containing a particular object type from
1752     * the parcel that was written with {@link #writeTypedList} at the
1753     * current dataPosition().  Returns null if the
1754     * previously written list object was null.  The list <em>must</em> have
1755     * previously been written via {@link #writeTypedList} with the same object
1756     * type.
1757     *
1758     * @return A newly created ArrayList containing objects with the same data
1759     *         as those that were previously written.
1760     *
1761     * @see #writeTypedList
1762     */
1763    public final <T> ArrayList<T> createTypedArrayList(Parcelable.Creator<T> c) {
1764        int N = readInt();
1765        if (N < 0) {
1766            return null;
1767        }
1768        ArrayList<T> l = new ArrayList<T>(N);
1769        while (N > 0) {
1770            if (readInt() != 0) {
1771                l.add(c.createFromParcel(this));
1772            } else {
1773                l.add(null);
1774            }
1775            N--;
1776        }
1777        return l;
1778    }
1779
1780    /**
1781     * Read into the given List items containing a particular object type
1782     * that were written with {@link #writeTypedList} at the
1783     * current dataPosition().  The list <em>must</em> have
1784     * previously been written via {@link #writeTypedList} with the same object
1785     * type.
1786     *
1787     * @return A newly created ArrayList containing objects with the same data
1788     *         as those that were previously written.
1789     *
1790     * @see #writeTypedList
1791     */
1792    public final <T> void readTypedList(List<T> list, Parcelable.Creator<T> c) {
1793        int M = list.size();
1794        int N = readInt();
1795        int i = 0;
1796        for (; i < M && i < N; i++) {
1797            if (readInt() != 0) {
1798                list.set(i, c.createFromParcel(this));
1799            } else {
1800                list.set(i, null);
1801            }
1802        }
1803        for (; i<N; i++) {
1804            if (readInt() != 0) {
1805                list.add(c.createFromParcel(this));
1806            } else {
1807                list.add(null);
1808            }
1809        }
1810        for (; i<M; i++) {
1811            list.remove(N);
1812        }
1813    }
1814
1815    /**
1816     * Read and return a new ArrayList containing String objects from
1817     * the parcel that was written with {@link #writeStringList} at the
1818     * current dataPosition().  Returns null if the
1819     * previously written list object was null.
1820     *
1821     * @return A newly created ArrayList containing strings with the same data
1822     *         as those that were previously written.
1823     *
1824     * @see #writeStringList
1825     */
1826    public final ArrayList<String> createStringArrayList() {
1827        int N = readInt();
1828        if (N < 0) {
1829            return null;
1830        }
1831        ArrayList<String> l = new ArrayList<String>(N);
1832        while (N > 0) {
1833            l.add(readString());
1834            N--;
1835        }
1836        return l;
1837    }
1838
1839    /**
1840     * Read and return a new ArrayList containing IBinder objects from
1841     * the parcel that was written with {@link #writeBinderList} at the
1842     * current dataPosition().  Returns null if the
1843     * previously written list object was null.
1844     *
1845     * @return A newly created ArrayList containing strings with the same data
1846     *         as those that were previously written.
1847     *
1848     * @see #writeBinderList
1849     */
1850    public final ArrayList<IBinder> createBinderArrayList() {
1851        int N = readInt();
1852        if (N < 0) {
1853            return null;
1854        }
1855        ArrayList<IBinder> l = new ArrayList<IBinder>(N);
1856        while (N > 0) {
1857            l.add(readStrongBinder());
1858            N--;
1859        }
1860        return l;
1861    }
1862
1863    /**
1864     * Read into the given List items String objects that were written with
1865     * {@link #writeStringList} at the current dataPosition().
1866     *
1867     * @return A newly created ArrayList containing strings with the same data
1868     *         as those that were previously written.
1869     *
1870     * @see #writeStringList
1871     */
1872    public final void readStringList(List<String> list) {
1873        int M = list.size();
1874        int N = readInt();
1875        int i = 0;
1876        for (; i < M && i < N; i++) {
1877            list.set(i, readString());
1878        }
1879        for (; i<N; i++) {
1880            list.add(readString());
1881        }
1882        for (; i<M; i++) {
1883            list.remove(N);
1884        }
1885    }
1886
1887    /**
1888     * Read into the given List items IBinder objects that were written with
1889     * {@link #writeBinderList} at the current dataPosition().
1890     *
1891     * @return A newly created ArrayList containing strings with the same data
1892     *         as those that were previously written.
1893     *
1894     * @see #writeBinderList
1895     */
1896    public final void readBinderList(List<IBinder> list) {
1897        int M = list.size();
1898        int N = readInt();
1899        int i = 0;
1900        for (; i < M && i < N; i++) {
1901            list.set(i, readStrongBinder());
1902        }
1903        for (; i<N; i++) {
1904            list.add(readStrongBinder());
1905        }
1906        for (; i<M; i++) {
1907            list.remove(N);
1908        }
1909    }
1910
1911    /**
1912     * Read and return a new array containing a particular object type from
1913     * the parcel at the current dataPosition().  Returns null if the
1914     * previously written array was null.  The array <em>must</em> have
1915     * previously been written via {@link #writeTypedArray} with the same
1916     * object type.
1917     *
1918     * @return A newly created array containing objects with the same data
1919     *         as those that were previously written.
1920     *
1921     * @see #writeTypedArray
1922     */
1923    public final <T> T[] createTypedArray(Parcelable.Creator<T> c) {
1924        int N = readInt();
1925        if (N < 0) {
1926            return null;
1927        }
1928        T[] l = c.newArray(N);
1929        for (int i=0; i<N; i++) {
1930            if (readInt() != 0) {
1931                l[i] = c.createFromParcel(this);
1932            }
1933        }
1934        return l;
1935    }
1936
1937    public final <T> void readTypedArray(T[] val, Parcelable.Creator<T> c) {
1938        int N = readInt();
1939        if (N == val.length) {
1940            for (int i=0; i<N; i++) {
1941                if (readInt() != 0) {
1942                    val[i] = c.createFromParcel(this);
1943                } else {
1944                    val[i] = null;
1945                }
1946            }
1947        } else {
1948            throw new RuntimeException("bad array lengths");
1949        }
1950    }
1951
1952    /**
1953     * @deprecated
1954     * @hide
1955     */
1956    @Deprecated
1957    public final <T> T[] readTypedArray(Parcelable.Creator<T> c) {
1958        return createTypedArray(c);
1959    }
1960
1961    /**
1962     * Write a heterogeneous array of Parcelable objects into the Parcel.
1963     * Each object in the array is written along with its class name, so
1964     * that the correct class can later be instantiated.  As a result, this
1965     * has significantly more overhead than {@link #writeTypedArray}, but will
1966     * correctly handle an array containing more than one type of object.
1967     *
1968     * @param value The array of objects to be written.
1969     * @param parcelableFlags Contextual flags as per
1970     * {@link Parcelable#writeToParcel(Parcel, int) Parcelable.writeToParcel()}.
1971     *
1972     * @see #writeTypedArray
1973     */
1974    public final <T extends Parcelable> void writeParcelableArray(T[] value,
1975            int parcelableFlags) {
1976        if (value != null) {
1977            int N = value.length;
1978            writeInt(N);
1979            for (int i=0; i<N; i++) {
1980                writeParcelable(value[i], parcelableFlags);
1981            }
1982        } else {
1983            writeInt(-1);
1984        }
1985    }
1986
1987    /**
1988     * Read a typed object from a parcel.  The given class loader will be
1989     * used to load any enclosed Parcelables.  If it is null, the default class
1990     * loader will be used.
1991     */
1992    public final Object readValue(ClassLoader loader) {
1993        int type = readInt();
1994
1995        switch (type) {
1996        case VAL_NULL:
1997            return null;
1998
1999        case VAL_STRING:
2000            return readString();
2001
2002        case VAL_INTEGER:
2003            return readInt();
2004
2005        case VAL_MAP:
2006            return readHashMap(loader);
2007
2008        case VAL_PARCELABLE:
2009            return readParcelable(loader);
2010
2011        case VAL_SHORT:
2012            return (short) readInt();
2013
2014        case VAL_LONG:
2015            return readLong();
2016
2017        case VAL_FLOAT:
2018            return readFloat();
2019
2020        case VAL_DOUBLE:
2021            return readDouble();
2022
2023        case VAL_BOOLEAN:
2024            return readInt() == 1;
2025
2026        case VAL_CHARSEQUENCE:
2027            return readCharSequence();
2028
2029        case VAL_LIST:
2030            return readArrayList(loader);
2031
2032        case VAL_BOOLEANARRAY:
2033            return createBooleanArray();
2034
2035        case VAL_BYTEARRAY:
2036            return createByteArray();
2037
2038        case VAL_STRINGARRAY:
2039            return readStringArray();
2040
2041        case VAL_CHARSEQUENCEARRAY:
2042            return readCharSequenceArray();
2043
2044        case VAL_IBINDER:
2045            return readStrongBinder();
2046
2047        case VAL_OBJECTARRAY:
2048            return readArray(loader);
2049
2050        case VAL_INTARRAY:
2051            return createIntArray();
2052
2053        case VAL_LONGARRAY:
2054            return createLongArray();
2055
2056        case VAL_BYTE:
2057            return readByte();
2058
2059        case VAL_SERIALIZABLE:
2060            return readSerializable();
2061
2062        case VAL_PARCELABLEARRAY:
2063            return readParcelableArray(loader);
2064
2065        case VAL_SPARSEARRAY:
2066            return readSparseArray(loader);
2067
2068        case VAL_SPARSEBOOLEANARRAY:
2069            return readSparseBooleanArray();
2070
2071        case VAL_BUNDLE:
2072            return readBundle(loader); // loading will be deferred
2073
2074        default:
2075            int off = dataPosition() - 4;
2076            throw new RuntimeException(
2077                "Parcel " + this + ": Unmarshalling unknown type code " + type + " at offset " + off);
2078        }
2079    }
2080
2081    /**
2082     * Read and return a new Parcelable from the parcel.  The given class loader
2083     * will be used to load any enclosed Parcelables.  If it is null, the default
2084     * class loader will be used.
2085     * @param loader A ClassLoader from which to instantiate the Parcelable
2086     * object, or null for the default class loader.
2087     * @return Returns the newly created Parcelable, or null if a null
2088     * object has been written.
2089     * @throws BadParcelableException Throws BadParcelableException if there
2090     * was an error trying to instantiate the Parcelable.
2091     */
2092    public final <T extends Parcelable> T readParcelable(ClassLoader loader) {
2093        Parcelable.Creator<T> creator = readParcelableCreator(loader);
2094        if (creator == null) {
2095            return null;
2096        }
2097        if (creator instanceof Parcelable.ClassLoaderCreator<?>) {
2098            return ((Parcelable.ClassLoaderCreator<T>)creator).createFromParcel(this, loader);
2099        }
2100        return creator.createFromParcel(this);
2101    }
2102
2103    /** @hide */
2104    public final <T extends Parcelable> T readCreator(Parcelable.Creator<T> creator,
2105            ClassLoader loader) {
2106        if (creator instanceof Parcelable.ClassLoaderCreator<?>) {
2107            return ((Parcelable.ClassLoaderCreator<T>)creator).createFromParcel(this, loader);
2108        }
2109        return creator.createFromParcel(this);
2110    }
2111
2112    /** @hide */
2113    public final <T extends Parcelable> Parcelable.Creator<T> readParcelableCreator(
2114            ClassLoader loader) {
2115        String name = readString();
2116        if (name == null) {
2117            return null;
2118        }
2119        Parcelable.Creator<T> creator;
2120        synchronized (mCreators) {
2121            HashMap<String,Parcelable.Creator> map = mCreators.get(loader);
2122            if (map == null) {
2123                map = new HashMap<String,Parcelable.Creator>();
2124                mCreators.put(loader, map);
2125            }
2126            creator = map.get(name);
2127            if (creator == null) {
2128                try {
2129                    Class c = loader == null ?
2130                        Class.forName(name) : Class.forName(name, true, loader);
2131                    Field f = c.getField("CREATOR");
2132                    creator = (Parcelable.Creator)f.get(null);
2133                }
2134                catch (IllegalAccessException e) {
2135                    Log.e(TAG, "Illegal access when unmarshalling: "
2136                                        + name, e);
2137                    throw new BadParcelableException(
2138                            "IllegalAccessException when unmarshalling: " + name);
2139                }
2140                catch (ClassNotFoundException e) {
2141                    Log.e(TAG, "Class not found when unmarshalling: "
2142                                        + name, e);
2143                    throw new BadParcelableException(
2144                            "ClassNotFoundException when unmarshalling: " + name);
2145                }
2146                catch (ClassCastException e) {
2147                    throw new BadParcelableException("Parcelable protocol requires a "
2148                                        + "Parcelable.Creator object called "
2149                                        + " CREATOR on class " + name);
2150                }
2151                catch (NoSuchFieldException e) {
2152                    throw new BadParcelableException("Parcelable protocol requires a "
2153                                        + "Parcelable.Creator object called "
2154                                        + " CREATOR on class " + name);
2155                }
2156                catch (NullPointerException e) {
2157                    throw new BadParcelableException("Parcelable protocol requires "
2158                            + "the CREATOR object to be static on class " + name);
2159                }
2160                if (creator == null) {
2161                    throw new BadParcelableException("Parcelable protocol requires a "
2162                                        + "Parcelable.Creator object called "
2163                                        + " CREATOR on class " + name);
2164                }
2165
2166                map.put(name, creator);
2167            }
2168        }
2169
2170        return creator;
2171    }
2172
2173    /**
2174     * Read and return a new Parcelable array from the parcel.
2175     * The given class loader will be used to load any enclosed
2176     * Parcelables.
2177     * @return the Parcelable array, or null if the array is null
2178     */
2179    public final Parcelable[] readParcelableArray(ClassLoader loader) {
2180        int N = readInt();
2181        if (N < 0) {
2182            return null;
2183        }
2184        Parcelable[] p = new Parcelable[N];
2185        for (int i = 0; i < N; i++) {
2186            p[i] = (Parcelable) readParcelable(loader);
2187        }
2188        return p;
2189    }
2190
2191    /**
2192     * Read and return a new Serializable object from the parcel.
2193     * @return the Serializable object, or null if the Serializable name
2194     * wasn't found in the parcel.
2195     */
2196    public final Serializable readSerializable() {
2197        String name = readString();
2198        if (name == null) {
2199            // For some reason we were unable to read the name of the Serializable (either there
2200            // is nothing left in the Parcel to read, or the next value wasn't a String), so
2201            // return null, which indicates that the name wasn't found in the parcel.
2202            return null;
2203        }
2204
2205        byte[] serializedData = createByteArray();
2206        ByteArrayInputStream bais = new ByteArrayInputStream(serializedData);
2207        try {
2208            ObjectInputStream ois = new ObjectInputStream(bais);
2209            return (Serializable) ois.readObject();
2210        } catch (IOException ioe) {
2211            throw new RuntimeException("Parcelable encountered " +
2212                "IOException reading a Serializable object (name = " + name +
2213                ")", ioe);
2214        } catch (ClassNotFoundException cnfe) {
2215            throw new RuntimeException("Parcelable encountered" +
2216                "ClassNotFoundException reading a Serializable object (name = "
2217                + name + ")", cnfe);
2218        }
2219    }
2220
2221    // Cache of previously looked up CREATOR.createFromParcel() methods for
2222    // particular classes.  Keys are the names of the classes, values are
2223    // Method objects.
2224    private static final HashMap<ClassLoader,HashMap<String,Parcelable.Creator>>
2225        mCreators = new HashMap<ClassLoader,HashMap<String,Parcelable.Creator>>();
2226
2227    static protected final Parcel obtain(int obj) {
2228        final Parcel[] pool = sHolderPool;
2229        synchronized (pool) {
2230            Parcel p;
2231            for (int i=0; i<POOL_SIZE; i++) {
2232                p = pool[i];
2233                if (p != null) {
2234                    pool[i] = null;
2235                    if (DEBUG_RECYCLE) {
2236                        p.mStack = new RuntimeException();
2237                    }
2238                    p.init(obj);
2239                    return p;
2240                }
2241            }
2242        }
2243        return new Parcel(obj);
2244    }
2245
2246    private Parcel(int nativePtr) {
2247        if (DEBUG_RECYCLE) {
2248            mStack = new RuntimeException();
2249        }
2250        //Log.i(TAG, "Initializing obj=0x" + Integer.toHexString(obj), mStack);
2251        init(nativePtr);
2252    }
2253
2254    private void init(int nativePtr) {
2255        if (nativePtr != 0) {
2256            mNativePtr = nativePtr;
2257            mOwnsNativeParcelObject = false;
2258        } else {
2259            mNativePtr = nativeCreate();
2260            mOwnsNativeParcelObject = true;
2261        }
2262    }
2263
2264    private void freeBuffer() {
2265        if (mOwnsNativeParcelObject) {
2266            nativeFreeBuffer(mNativePtr);
2267        }
2268    }
2269
2270    private void destroy() {
2271        if (mNativePtr != 0) {
2272            if (mOwnsNativeParcelObject) {
2273                nativeDestroy(mNativePtr);
2274            }
2275            mNativePtr = 0;
2276        }
2277    }
2278
2279    @Override
2280    protected void finalize() throws Throwable {
2281        if (DEBUG_RECYCLE) {
2282            if (mStack != null) {
2283                Log.w(TAG, "Client did not call Parcel.recycle()", mStack);
2284            }
2285        }
2286        destroy();
2287    }
2288
2289    /* package */ void readMapInternal(Map outVal, int N,
2290        ClassLoader loader) {
2291        while (N > 0) {
2292            Object key = readValue(loader);
2293            Object value = readValue(loader);
2294            outVal.put(key, value);
2295            N--;
2296        }
2297    }
2298
2299    /* package */ void readArrayMapInternal(ArrayMap outVal, int N,
2300        ClassLoader loader) {
2301        if (DEBUG_ARRAY_MAP) {
2302            RuntimeException here =  new RuntimeException("here");
2303            here.fillInStackTrace();
2304            Log.d(TAG, "Reading " + N + " ArrayMap entries", here);
2305        }
2306        while (N > 0) {
2307            Object key = readValue(loader);
2308            if (DEBUG_ARRAY_MAP) Log.d(TAG, "  Read #" + (N-1) + ": key=0x"
2309                    + (key != null ? key.hashCode() : 0) + " " + key);
2310            Object value = readValue(loader);
2311            outVal.append(key, value);
2312            N--;
2313        }
2314    }
2315
2316    /* package */ void readArrayMapSafelyInternal(ArrayMap outVal, int N,
2317        ClassLoader loader) {
2318        if (DEBUG_ARRAY_MAP) {
2319            RuntimeException here =  new RuntimeException("here");
2320            here.fillInStackTrace();
2321            Log.d(TAG, "Reading safely " + N + " ArrayMap entries", here);
2322        }
2323        while (N > 0) {
2324            Object key = readValue(loader);
2325            if (DEBUG_ARRAY_MAP) Log.d(TAG, "  Read safe #" + (N-1) + ": key=0x"
2326                    + (key != null ? key.hashCode() : 0) + " " + key);
2327            Object value = readValue(loader);
2328            outVal.put(key, value);
2329            N--;
2330        }
2331    }
2332
2333    private void readListInternal(List outVal, int N,
2334        ClassLoader loader) {
2335        while (N > 0) {
2336            Object value = readValue(loader);
2337            //Log.d(TAG, "Unmarshalling value=" + value);
2338            outVal.add(value);
2339            N--;
2340        }
2341    }
2342
2343    private void readArrayInternal(Object[] outVal, int N,
2344        ClassLoader loader) {
2345        for (int i = 0; i < N; i++) {
2346            Object value = readValue(loader);
2347            //Log.d(TAG, "Unmarshalling value=" + value);
2348            outVal[i] = value;
2349        }
2350    }
2351
2352    private void readSparseArrayInternal(SparseArray outVal, int N,
2353        ClassLoader loader) {
2354        while (N > 0) {
2355            int key = readInt();
2356            Object value = readValue(loader);
2357            //Log.i(TAG, "Unmarshalling key=" + key + " value=" + value);
2358            outVal.append(key, value);
2359            N--;
2360        }
2361    }
2362
2363
2364    private void readSparseBooleanArrayInternal(SparseBooleanArray outVal, int N) {
2365        while (N > 0) {
2366            int key = readInt();
2367            boolean value = this.readByte() == 1;
2368            //Log.i(TAG, "Unmarshalling key=" + key + " value=" + value);
2369            outVal.append(key, value);
2370            N--;
2371        }
2372    }
2373}
2374