Parcel.cpp revision 2f10ae08d435b12e1798d93e0b90605717c66081
154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project/*
254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * Copyright (C) 2005 The Android Open Source Project
354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project *
454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * you may not use this file except in compliance with the License.
654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * You may obtain a copy of the License at
754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project *
854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project *
1054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
1154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
1254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * See the License for the specific language governing permissions and
1454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project * limitations under the License.
1554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project */
1654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
1754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#define LOG_TAG "Parcel"
1854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project//#define LOG_NDEBUG 0
1954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
200795272aa226f4e965968a03daddc53ce30b7cdaMathias Agopian#include <binder/Parcel.h>
2154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
220795272aa226f4e965968a03daddc53ce30b7cdaMathias Agopian#include <binder/Binder.h>
230795272aa226f4e965968a03daddc53ce30b7cdaMathias Agopian#include <binder/BpBinder.h>
2454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/Debug.h>
250795272aa226f4e965968a03daddc53ce30b7cdaMathias Agopian#include <binder/ProcessState.h>
2654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/Log.h>
2754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/String8.h>
2854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/String16.h>
2954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/TextOutput.h>
3054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <utils/misc.h>
3154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
3225ba5b6564224dceefa086b5c439ef28dad530caMathias Agopian#include <private/binder/binder_module.h>
3354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
3454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <stdio.h>
3554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <stdlib.h>
3654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#include <stdint.h>
3754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
3854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#ifndef INT32_MAX
3954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#define INT32_MAX ((int32_t)(2147483647))
4054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#endif
4154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
4254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#define LOG_REFS(...)
4354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project//#define LOG_REFS(...) LOG(LOG_DEBUG, "Parcel", __VA_ARGS__)
4454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
4554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project// ---------------------------------------------------------------------------
4654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
4754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#define PAD_SIZE(s) (((s)+3)&~3)
4854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
4954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project// XXX This can be made public if we want to provide
5054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project// support for typed data.
5154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstruct small_flat_data
5254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
5354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint32_t type;
5454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint32_t data;
5554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project};
5654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
5754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectnamespace android {
5854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
5954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid acquire_object(const sp<ProcessState>& proc,
6054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const flat_binder_object& obj, const void* who)
6154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
6254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    switch (obj.type) {
6354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_BINDER:
6454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (obj.binder) {
6554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOG_REFS("Parcel %p acquiring reference on local %p", who, obj.cookie);
6654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                static_cast<IBinder*>(obj.cookie)->incStrong(who);
6754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
6854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
6954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_WEAK_BINDER:
7054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (obj.binder)
7154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                static_cast<RefBase::weakref_type*>(obj.binder)->incWeak(who);
7254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
7354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_HANDLE: {
7454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const sp<IBinder> b = proc->getStrongProxyForHandle(obj.handle);
7554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (b != NULL) {
7654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOG_REFS("Parcel %p acquiring reference on remote %p", who, b.get());
7754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                b->incStrong(who);
7854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
7954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
8054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
8154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_WEAK_HANDLE: {
8254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const wp<IBinder> b = proc->getWeakProxyForHandle(obj.handle);
8354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (b != NULL) b.get_refs()->incWeak(who);
8454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
8554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
8654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_FD: {
8754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // intentionally blank -- nothing to do to acquire this, but we do
8854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // recognize it as a legitimate object type.
8954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
9054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
9154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
9254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
9354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGD("Invalid object type 0x%08lx", obj.type);
9454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
9554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
9654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid release_object(const sp<ProcessState>& proc,
9754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const flat_binder_object& obj, const void* who)
9854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
9954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    switch (obj.type) {
10054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_BINDER:
10154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (obj.binder) {
10254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOG_REFS("Parcel %p releasing reference on local %p", who, obj.cookie);
10354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                static_cast<IBinder*>(obj.cookie)->decStrong(who);
10454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
10554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
10654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_WEAK_BINDER:
10754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (obj.binder)
10854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                static_cast<RefBase::weakref_type*>(obj.binder)->decWeak(who);
10954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
11054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_HANDLE: {
11154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const sp<IBinder> b = proc->getStrongProxyForHandle(obj.handle);
11254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (b != NULL) {
11354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOG_REFS("Parcel %p releasing reference on remote %p", who, b.get());
11454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                b->decStrong(who);
11554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
11654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
11754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
11854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_WEAK_HANDLE: {
11954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const wp<IBinder> b = proc->getWeakProxyForHandle(obj.handle);
12054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (b != NULL) b.get_refs()->decWeak(who);
12154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
12254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
12354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        case BINDER_TYPE_FD: {
12454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (obj.cookie != (void*)0) close(obj.handle);
12554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return;
12654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
12754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
12854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
12954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGE("Invalid object type 0x%08lx", obj.type);
13054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
13154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
13254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectinline static status_t finish_flatten_binder(
13354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const sp<IBinder>& binder, const flat_binder_object& flat, Parcel* out)
13454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
13554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return out->writeObject(flat, false);
13654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
13754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
13854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t flatten_binder(const sp<ProcessState>& proc,
13954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const sp<IBinder>& binder, Parcel* out)
14054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
14154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    flat_binder_object obj;
14254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
14354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
14454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (binder != NULL) {
14554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        IBinder *local = binder->localBinder();
14654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (!local) {
14754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            BpBinder *proxy = binder->remoteBinder();
14854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (proxy == NULL) {
14954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGE("null proxy");
15054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
15154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const int32_t handle = proxy ? proxy->handle() : 0;
15254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.type = BINDER_TYPE_HANDLE;
15354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.handle = handle;
15454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.cookie = NULL;
15554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        } else {
15654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.type = BINDER_TYPE_BINDER;
15754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.binder = local->getWeakRefs();
15854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            obj.cookie = local;
15954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
16054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
16154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.type = BINDER_TYPE_BINDER;
16254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.binder = NULL;
16354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.cookie = NULL;
16454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
16554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
16654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return finish_flatten_binder(binder, obj, out);
16754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
16854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
16954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t flatten_binder(const sp<ProcessState>& proc,
17054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const wp<IBinder>& binder, Parcel* out)
17154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
17254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    flat_binder_object obj;
17354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
17454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
17554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (binder != NULL) {
17654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        sp<IBinder> real = binder.promote();
17754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (real != NULL) {
17854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            IBinder *local = real->localBinder();
17954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (!local) {
18054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                BpBinder *proxy = real->remoteBinder();
18154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                if (proxy == NULL) {
18254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    LOGE("null proxy");
18354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                }
18454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                const int32_t handle = proxy ? proxy->handle() : 0;
18554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.type = BINDER_TYPE_WEAK_HANDLE;
18654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.handle = handle;
18754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.cookie = NULL;
18854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            } else {
18954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.type = BINDER_TYPE_WEAK_BINDER;
19054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.binder = binder.get_refs();
19154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                obj.cookie = binder.unsafe_get();
19254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
19354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return finish_flatten_binder(real, obj, out);
19454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
19554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
19654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // XXX How to deal?  In order to flatten the given binder,
19754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // we need to probe it for information, which requires a primary
19854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // reference...  but we don't have one.
19954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        //
20054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // The OpenBinder implementation uses a dynamic_cast<> here,
20154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // but we can't do that with the different reference counting
20254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // implementation we are using.
20354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGE("Unable to unflatten Binder weak reference!");
20454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.type = BINDER_TYPE_BINDER;
20554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.binder = NULL;
20654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.cookie = NULL;
20754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return finish_flatten_binder(NULL, obj, out);
20854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
20954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
21054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.type = BINDER_TYPE_BINDER;
21154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.binder = NULL;
21254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        obj.cookie = NULL;
21354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return finish_flatten_binder(NULL, obj, out);
21454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
21554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
21654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
21754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectinline static status_t finish_unflatten_binder(
21854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    BpBinder* proxy, const flat_binder_object& flat, const Parcel& in)
21954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
22054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
22154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
22254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
22354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t unflatten_binder(const sp<ProcessState>& proc,
22454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const Parcel& in, sp<IBinder>* out)
22554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
22654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const flat_binder_object* flat = in.readObject(false);
22754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
22854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (flat) {
22954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        switch (flat->type) {
23054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_BINDER:
23154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                *out = static_cast<IBinder*>(flat->cookie);
23254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return finish_unflatten_binder(NULL, *flat, in);
23354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_HANDLE:
23454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                *out = proc->getStrongProxyForHandle(flat->handle);
23554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return finish_unflatten_binder(
23654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    static_cast<BpBinder*>(out->get()), *flat, in);
23754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
23854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
23954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return BAD_TYPE;
24054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
24154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
24254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t unflatten_binder(const sp<ProcessState>& proc,
24354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const Parcel& in, wp<IBinder>* out)
24454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
24554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const flat_binder_object* flat = in.readObject(false);
24654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
24754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (flat) {
24854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        switch (flat->type) {
24954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_BINDER:
25054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                *out = static_cast<IBinder*>(flat->cookie);
25154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return finish_unflatten_binder(NULL, *flat, in);
25254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_WEAK_BINDER:
25354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                if (flat->binder != NULL) {
25454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    out->set_object_and_refs(
25554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                        static_cast<IBinder*>(flat->cookie),
25654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                        static_cast<RefBase::weakref_type*>(flat->binder));
25754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                } else {
25854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    *out = NULL;
25954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                }
26054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return finish_unflatten_binder(NULL, *flat, in);
26154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_HANDLE:
26254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_WEAK_HANDLE:
26354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                *out = proc->getWeakProxyForHandle(flat->handle);
26454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return finish_unflatten_binder(
26554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    static_cast<BpBinder*>(out->unsafe_get()), *flat, in);
26654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
26754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
26854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return BAD_TYPE;
26954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
27054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
27154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project// ---------------------------------------------------------------------------
27254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
27354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source ProjectParcel::Parcel()
27454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
27554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    initState();
27654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
27754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
27854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source ProjectParcel::~Parcel()
27954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
28054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    freeDataNoInit();
28154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
28254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
28354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst uint8_t* Parcel::data() const
28454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
28554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mData;
28654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
28754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
28854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::dataSize() const
28954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
29054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return (mDataSize > mDataPos ? mDataSize : mDataPos);
29154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
29254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
29354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::dataAvail() const
29454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
29554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // TODO: decide what to do about the possibility that this can
29654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // report an available-data size that exceeds a Java int's max
29754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // positive value, causing havoc.  Fortunately this will only
29854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // happen if someone constructs a Parcel containing more than two
29954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // gigabytes of data, which on typical phone hardware is simply
30054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // not possible.
30154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return dataSize() - dataPosition();
30254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
30354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
30454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::dataPosition() const
30554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
30654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mDataPos;
30754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
30854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
30954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::dataCapacity() const
31054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
31154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mDataCapacity;
31254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
31354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
31454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::setDataSize(size_t size)
31554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
31654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err;
31754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    err = continueWrite(size);
31854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) {
31954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataSize = size;
32054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("setDataSize Setting data size of %p to %d\n", this, mDataSize);
32154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
32254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return err;
32354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
32454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
32554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::setDataPosition(size_t pos) const
32654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
32754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataPos = pos;
32854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mNextObjectHint = 0;
32954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
33054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
33154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::setDataCapacity(size_t size)
33254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
33354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (size > mDataSize) return continueWrite(size);
33454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
33554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
33654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
33754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::setData(const uint8_t* buffer, size_t len)
33854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
33954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err = restartWrite(len);
34054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) {
34154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        memcpy(const_cast<uint8_t*>(data()), buffer, len);
34254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataSize = len;
34354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mFdsKnown = false;
34454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
34554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return err;
34654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
34754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
34854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::appendFrom(Parcel *parcel, size_t offset, size_t len)
34954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
35054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const sp<ProcessState> proc(ProcessState::self());
35154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err;
35254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint8_t *data = parcel->mData;
35354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t *objects = parcel->mObjects;
35454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t size = parcel->mObjectsSize;
35554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    int startPos = mDataPos;
35654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    int firstIndex = -1, lastIndex = -2;
35754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
35854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (len == 0) {
35954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NO_ERROR;
36054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
36154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
36254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // range checks against the source parcel size
36354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if ((offset > parcel->mDataSize)
36454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            || (len > parcel->mDataSize)
36554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            || (offset + len > parcel->mDataSize)) {
36654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return BAD_VALUE;
36754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
36854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
36954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // Count objects in range
37054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    for (int i = 0; i < (int) size; i++) {
37154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t off = objects[i];
37254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if ((off >= offset) && (off < offset + len)) {
37354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (firstIndex == -1) {
37454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                firstIndex = i;
37554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
37654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            lastIndex = i;
37754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
37854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
37954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    int numObjects = lastIndex - firstIndex + 1;
38054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
38154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // grow data
38254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    err = growData(len);
38354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err != NO_ERROR) {
38454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return err;
38554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
38654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
38754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // append data
38854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    memcpy(mData + mDataPos, data + offset, len);
38954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataPos += len;
39054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataSize += len;
39154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
39254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (numObjects > 0) {
39354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // grow objects
39454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (mObjectsCapacity < mObjectsSize + numObjects) {
39554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            int newSize = ((mObjectsSize + numObjects)*3)/2;
39654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            size_t *objects =
39754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                (size_t*)realloc(mObjects, newSize*sizeof(size_t));
39854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (objects == (size_t*)0) {
39954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return NO_MEMORY;
40054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
40154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjects = objects;
40254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsCapacity = newSize;
40354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
40454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
40554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // append and acquire objects
40654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        int idx = mObjectsSize;
40754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        for (int i = firstIndex; i <= lastIndex; i++) {
40854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            size_t off = objects[i] - offset + startPos;
40954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjects[idx++] = off;
41054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsSize++;
41154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
4126aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn            flat_binder_object* flat
41354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                = reinterpret_cast<flat_binder_object*>(mData + off);
41454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            acquire_object(proc, *flat, this);
41554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
41654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (flat->type == BINDER_TYPE_FD) {
4176aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn                // If this is a file descriptor, we need to dup it so the
4186aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn                // new Parcel now owns its own fd, and can declare that we
4196aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn                // officially know we have fds.
4206aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn                flat->handle = dup(flat->handle);
4216aff905048ba3b03724f17e2aba9089872e14cd2Dianne Hackborn                flat->cookie = (void*)1;
42254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mHasFds = mFdsKnown = true;
42354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
42454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
42554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
42654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
42754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
42854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
42954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
43054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectbool Parcel::hasFileDescriptors() const
43154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
43254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (!mFdsKnown) {
43354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        scanForFds();
43454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
43554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mHasFds;
43654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
43754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
43854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeInterfaceToken(const String16& interface)
43954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
44054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // currently the interface identification token is just its name as a string
44154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return writeString16(interface);
44254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
44354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
444aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopianbool Parcel::checkInterface(IBinder* binder) const
445aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopian{
446aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopian    return enforceInterface(binder->getInterfaceDescriptor());
447aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopian}
448aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopian
44954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectbool Parcel::enforceInterface(const String16& interface) const
45054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
451aaf834a284a025cedd8ec1cf01d09e1790c1dcf8Mathias Agopian    const String16 str(readString16());
45254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (str == interface) {
45354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return true;
45454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
45554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGW("**** enforceInterface() expected '%s' but read '%s'\n",
45654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                String8(interface).string(), String8(str).string());
45754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return false;
45854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
45954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
46054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
46154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst size_t* Parcel::objects() const
46254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
46354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mObjects;
46454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
46554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
46654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::objectsCount() const
46754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
46854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mObjectsSize;
46954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
47054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
47154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::errorCheck() const
47254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
47354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mError;
47454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
47554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
47654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::setError(status_t err)
47754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
47854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mError = err;
47954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
48054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
48154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::finishWrite(size_t len)
48254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
48354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    //printf("Finish write of %d\n", len);
48454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataPos += len;
48554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("finishWrite Setting data pos of %p to %d\n", this, mDataPos);
48654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (mDataPos > mDataSize) {
48754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataSize = mDataPos;
48854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("finishWrite Setting data size of %p to %d\n", this, mDataSize);
48954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
49054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    //printf("New pos=%d, size=%d\n", mDataPos, mDataSize);
49154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
49254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
49354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
49454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeUnpadded(const void* data, size_t len)
49554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
49654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t end = mDataPos + len;
49754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (end < mDataPos) {
49854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // integer overflow
49954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return BAD_VALUE;
50054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
50154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
50254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (end <= mDataCapacity) {
50354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectrestart_write:
50454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        memcpy(mData+mDataPos, data, len);
50554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return finishWrite(len);
50654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
50754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
50854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err = growData(len);
50954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) goto restart_write;
51054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return err;
51154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
51254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
51354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::write(const void* data, size_t len)
51454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
51554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    void* const d = writeInplace(len);
51654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (d) {
51754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        memcpy(d, data, len);
51854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NO_ERROR;
51954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
52054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mError;
52154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
52254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
52354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid* Parcel::writeInplace(size_t len)
52454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
52554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const size_t padded = PAD_SIZE(len);
52654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
52754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // sanity check for integer overflow
52854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (mDataPos+padded < mDataPos) {
52954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NULL;
53054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
53154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
53254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if ((mDataPos+padded) <= mDataCapacity) {
53354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectrestart_write:
53454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        //printf("Writing %ld bytes, padded to %ld\n", len, padded);
53554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        uint8_t* const data = mData+mDataPos;
53654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
53754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // Need to pad at end?
53854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (padded != len) {
53954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#if BYTE_ORDER == BIG_ENDIAN
54054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            static const uint32_t mask[4] = {
54154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                0x00000000, 0xffffff00, 0xffff0000, 0xff000000
54254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            };
54354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#endif
54454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#if BYTE_ORDER == LITTLE_ENDIAN
54554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            static const uint32_t mask[4] = {
54654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                0x00000000, 0x00ffffff, 0x0000ffff, 0x000000ff
54754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            };
54854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project#endif
54954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            //printf("Applying pad mask: %p to %p\n", (void*)mask[padded-len],
55054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            //    *reinterpret_cast<void**>(data+padded-4));
55154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            *reinterpret_cast<uint32_t*>(data+padded-4) &= mask[padded-len];
55254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
55354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
55454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        finishWrite(padded);
55554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return data;
55654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
55754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
55854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err = growData(padded);
55954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) goto restart_write;
56054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NULL;
56154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
56254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
56354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeInt32(int32_t val)
56454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
5652f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return writeAligned(val);
56654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
56754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
56854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeInt64(int64_t val)
56954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
5702f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return writeAligned(val);
57154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
57254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
57354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeFloat(float val)
57454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
5752f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return writeAligned(val);
57654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
57754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
57854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeDouble(double val)
57954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
5802f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return writeAligned(val);
5812f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
58254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
5832f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberstatus_t Parcel::writeIntPtr(intptr_t val)
5842f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber{
5852f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return writeAligned(val);
58654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
58754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
58854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeCString(const char* str)
58954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
59054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return write(str, strlen(str)+1);
59154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
59254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
59354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeString8(const String8& str)
59454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
59554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err = writeInt32(str.bytes());
59654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) {
59754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        err = write(str.string(), str.bytes()+1);
59854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
59954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return err;
60054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
60154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
60254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeString16(const String16& str)
60354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
60454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return writeString16(str.string(), str.size());
60554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
60654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
60754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeString16(const char16_t* str, size_t len)
60854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
60954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (str == NULL) return writeInt32(-1);
61054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
61154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    status_t err = writeInt32(len);
61254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (err == NO_ERROR) {
61354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        len *= sizeof(char16_t);
61454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        uint8_t* data = (uint8_t*)writeInplace(len+sizeof(char16_t));
61554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (data) {
61654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            memcpy(data, str, len);
61754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            *reinterpret_cast<char16_t*>(data+len) = 0;
61854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return NO_ERROR;
61954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
62054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        err = mError;
62154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
62254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return err;
62354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
62454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
62554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeStrongBinder(const sp<IBinder>& val)
62654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
62754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return flatten_binder(ProcessState::self(), val, this);
62854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
62954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
63054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeWeakBinder(const wp<IBinder>& val)
63154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
63254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return flatten_binder(ProcessState::self(), val, this);
63354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
63454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
635dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopianstatus_t Parcel::writeNativeHandle(const native_handle* handle)
63622f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project{
637f1db4aec6569d7cf9e1fb84f1d9c1292032eac30Mathias Agopian    if (!handle || handle->version != sizeof(native_handle))
63822f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project        return BAD_TYPE;
63922f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
64022f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    status_t err;
641dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian    err = writeInt32(handle->numFds);
64222f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    if (err != NO_ERROR) return err;
6439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
644dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian    err = writeInt32(handle->numInts);
64522f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    if (err != NO_ERROR) return err;
6469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
647dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian    for (int i=0 ; err==NO_ERROR && i<handle->numFds ; i++)
648dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian        err = writeDupFileDescriptor(handle->data[i]);
6499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (err != NO_ERROR) {
6519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        LOGD("write native handle, write dup fd failed");
6529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return err;
6539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
654dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian    err = write(handle->data + handle->numFds, sizeof(int)*handle->numInts);
65522f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    return err;
65622f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project}
65722f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
65854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeFileDescriptor(int fd)
65954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
66054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    flat_binder_object obj;
66154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.type = BINDER_TYPE_FD;
66254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
66354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.handle = fd;
66454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.cookie = (void*)0;
66554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return writeObject(obj, true);
66654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
66754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
66854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeDupFileDescriptor(int fd)
66954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
67054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    flat_binder_object obj;
67154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.type = BINDER_TYPE_FD;
67254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
67354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.handle = dup(fd);
67454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    obj.cookie = (void*)1;
67554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return writeObject(obj, true);
67654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
67754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
67854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::writeObject(const flat_binder_object& val, bool nullMetaData)
67954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
68054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const bool enoughData = (mDataPos+sizeof(val)) <= mDataCapacity;
68154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const bool enoughObjects = mObjectsSize < mObjectsCapacity;
68254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (enoughData && enoughObjects) {
68354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectrestart_write:
68454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        *reinterpret_cast<flat_binder_object*>(mData+mDataPos) = val;
68554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
68654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // Need to write meta-data?
68754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (nullMetaData || val.binder != NULL) {
68854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjects[mObjectsSize] = mDataPos;
68954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            acquire_object(ProcessState::self(), val, this);
69054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsSize++;
69154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
69254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
69354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // remember if it's a file descriptor
69454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (val.type == BINDER_TYPE_FD) {
69554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mHasFds = mFdsKnown = true;
69654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
69754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
69854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return finishWrite(sizeof(flat_binder_object));
69954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
70054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
70154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (!enoughData) {
70254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const status_t err = growData(sizeof(val));
70354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (err != NO_ERROR) return err;
70454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
70554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (!enoughObjects) {
70654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t newSize = ((mObjectsSize+2)*3)/2;
70754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t* objects = (size_t*)realloc(mObjects, newSize*sizeof(size_t));
70854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (objects == NULL) return NO_MEMORY;
70954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mObjects = objects;
71054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mObjectsCapacity = newSize;
71154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
71254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
71354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    goto restart_write;
71454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
71554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
71654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
71754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::remove(size_t start, size_t amt)
71854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
71954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOG_ALWAYS_FATAL("Parcel::remove() not yet implemented!");
72054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
72154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
72254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::read(void* outData, size_t len) const
72354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
72454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if ((mDataPos+PAD_SIZE(len)) >= mDataPos && (mDataPos+PAD_SIZE(len)) <= mDataSize) {
72554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        memcpy(outData, mData+mDataPos, len);
72654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataPos += PAD_SIZE(len);
72754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("read Setting data pos of %p to %d\n", this, mDataPos);
72854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NO_ERROR;
72954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
73054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NOT_ENOUGH_DATA;
73154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
73254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
73354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst void* Parcel::readInplace(size_t len) const
73454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
73554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if ((mDataPos+PAD_SIZE(len)) >= mDataPos && (mDataPos+PAD_SIZE(len)) <= mDataSize) {
73654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const void* data = mData+mDataPos;
73754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataPos += PAD_SIZE(len);
73854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("readInplace Setting data pos of %p to %d\n", this, mDataPos);
73954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return data;
74054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
74154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NULL;
74254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
74354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
7442f10ae08d435b12e1798d93e0b90605717c66081Andreas Hubertemplate<class T>
7452f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberstatus_t Parcel::readAligned(T *pArg) const {
7462f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    COMPILE_TIME_ASSERT_FUNCTION_SCOPE(PAD_SIZE(sizeof(T)) == sizeof(T));
7472f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7482f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    if ((mDataPos+sizeof(T)) <= mDataSize) {
74954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const void* data = mData+mDataPos;
7502f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber        mDataPos += sizeof(T);
7512f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber        *pArg =  *reinterpret_cast<const T*>(data);
75254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NO_ERROR;
75354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
75454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NOT_ENOUGH_DATA;
75554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
75654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
75754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
7582f10ae08d435b12e1798d93e0b90605717c66081Andreas Hubertemplate<class T>
7592f10ae08d435b12e1798d93e0b90605717c66081Andreas HuberT Parcel::readAligned() const {
7602f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    T result;
7612f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    if (readAligned(&result) != NO_ERROR) {
7622f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber        result = 0;
7632f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    }
7642f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7652f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return result;
7662f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
7672f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7682f10ae08d435b12e1798d93e0b90605717c66081Andreas Hubertemplate<class T>
7692f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberstatus_t Parcel::writeAligned(T val) {
7702f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    COMPILE_TIME_ASSERT_FUNCTION_SCOPE(PAD_SIZE(sizeof(T)) == sizeof(T));
7712f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7722f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    if ((mDataPos+sizeof(val)) <= mDataCapacity) {
7732f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberrestart_write:
7742f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber        *reinterpret_cast<T*>(mData+mDataPos) = val;
7752f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber        return finishWrite(sizeof(val));
7762f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    }
7772f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7782f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    status_t err = growData(sizeof(val));
7792f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    if (err == NO_ERROR) goto restart_write;
7802f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return err;
7812f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
7822f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
7832f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberstatus_t Parcel::readInt32(int32_t *pArg) const
7842f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber{
7852f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned(pArg);
7862f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
7872f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
78854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectint32_t Parcel::readInt32() const
78954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
7902f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned<int32_t>();
79154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
79254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
79354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
79454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::readInt64(int64_t *pArg) const
79554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
7962f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned(pArg);
79754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
79854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
79954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
80054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectint64_t Parcel::readInt64() const
80154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
8022f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned<int64_t>();
80354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
80454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
80554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::readFloat(float *pArg) const
80654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
8072f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned(pArg);
80854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
80954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
81054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
81154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectfloat Parcel::readFloat() const
81254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
8132f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned<float>();
81454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
81554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
81654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::readDouble(double *pArg) const
81754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
8182f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned(pArg);
81954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
82054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
82154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
82254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectdouble Parcel::readDouble() const
82354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
8242f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned<double>();
8252f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
8262f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
8272f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberstatus_t Parcel::readIntPtr(intptr_t *pArg) const
8282f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber{
8292f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned(pArg);
8302f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber}
8312f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
8322f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber
8332f10ae08d435b12e1798d93e0b90605717c66081Andreas Huberintptr_t Parcel::readIntPtr() const
8342f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber{
8352f10ae08d435b12e1798d93e0b90605717c66081Andreas Huber    return readAligned<intptr_t>();
83654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
83754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
83854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
83954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst char* Parcel::readCString() const
84054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
84154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const size_t avail = mDataSize-mDataPos;
84254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (avail > 0) {
84354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const char* str = reinterpret_cast<const char*>(mData+mDataPos);
84454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // is the string's trailing NUL within the parcel's valid bounds?
84554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const char* eos = reinterpret_cast<const char*>(memchr(str, 0, avail));
84654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (eos) {
84754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const size_t len = eos - str;
84854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mDataPos += PAD_SIZE(len+1);
84954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            LOGV("readCString Setting data pos of %p to %d\n", this, mDataPos);
85054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return str;
85154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
85254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
85354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NULL;
85454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
85554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
85654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source ProjectString8 Parcel::readString8() const
85754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
85854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    int32_t size = readInt32();
85954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // watch for potential int overflow adding 1 for trailing NUL
86054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (size > 0 && size < INT32_MAX) {
86154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const char* str = (const char*)readInplace(size+1);
86254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (str) return String8(str, size);
86354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
86454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return String8();
86554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
86654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
86754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source ProjectString16 Parcel::readString16() const
86854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
86954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t len;
87054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const char16_t* str = readString16Inplace(&len);
87154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (str) return String16(str, len);
87254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGE("Reading a NULL string not supported here.");
87354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return String16();
87454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
87554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
87654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst char16_t* Parcel::readString16Inplace(size_t* outLen) const
87754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
87854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    int32_t size = readInt32();
87954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // watch for potential int overflow from size+1
88054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (size >= 0 && size < INT32_MAX) {
88154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        *outLen = size;
88254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const char16_t* str = (const char16_t*)readInplace((size+1)*sizeof(char16_t));
88354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (str != NULL) {
88454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return str;
88554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
88654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
88754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    *outLen = 0;
88854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NULL;
88954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
89054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
89154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsp<IBinder> Parcel::readStrongBinder() const
89254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
89354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    sp<IBinder> val;
89454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    unflatten_binder(ProcessState::self(), *this, &val);
89554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return val;
89654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
89754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
89854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectwp<IBinder> Parcel::readWeakBinder() const
89954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
90054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    wp<IBinder> val;
90154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    unflatten_binder(ProcessState::self(), *this, &val);
90254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return val;
90354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
90454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
90522f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
906dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopiannative_handle* Parcel::readNativeHandle() const
90722f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project{
90822f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    int numFds, numInts;
90922f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    status_t err;
91022f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    err = readInt32(&numFds);
91122f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    if (err != NO_ERROR) return 0;
91222f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    err = readInt32(&numInts);
91322f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    if (err != NO_ERROR) return 0;
91422f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
915dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian    native_handle* h = native_handle_create(numFds, numInts);
91622f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    for (int i=0 ; err==NO_ERROR && i<numFds ; i++) {
917bc4afde167513f7efe76012015f9fa3641c156cfRebecca Schultz Zavin        h->data[i] = dup(readFileDescriptor());
91822f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project        if (h->data[i] < 0) err = BAD_VALUE;
91922f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    }
92022f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    err = read(h->data + numFds, sizeof(int)*numInts);
92122f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    if (err != NO_ERROR) {
922dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian        native_handle_close(h);
923dfece80c790934e4413def863070ac0dd21f6e29Mathias Agopian        native_handle_delete(h);
92422f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project        h = 0;
92522f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    }
92622f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project    return h;
92722f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project}
92822f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
92922f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project
93054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectint Parcel::readFileDescriptor() const
93154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
93254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const flat_binder_object* flat = readObject(true);
93354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (flat) {
93454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        switch (flat->type) {
93554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            case BINDER_TYPE_FD:
93654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                //LOGI("Returning file descriptor %ld from parcel %p\n", flat->handle, this);
93754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return flat->handle;
93854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
93954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
94054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return BAD_TYPE;
94154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
94254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
94354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst flat_binder_object* Parcel::readObject(bool nullMetaData) const
94454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
94554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const size_t DPOS = mDataPos;
94654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if ((DPOS+sizeof(flat_binder_object)) <= mDataSize) {
94754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const flat_binder_object* obj
94854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                = reinterpret_cast<const flat_binder_object*>(mData+DPOS);
94954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataPos = DPOS + sizeof(flat_binder_object);
95054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (!nullMetaData && (obj->cookie == NULL && obj->binder == NULL)) {
95122f7dfd23490a3de2f21ff96949ba47003aac8f8The Android Open Source Project            // When transferring a NULL object, we don't write it into
95254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // the object list, so we don't want to check for it when
95354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // reading.
95454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            LOGV("readObject Setting data pos of %p to %d\n", this, mDataPos);
95554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return obj;
95654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
95754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
95854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // Ensure that this object is valid...
95954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t* const OBJS = mObjects;
96054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const size_t N = mObjectsSize;
96154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t opos = mNextObjectHint;
96254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
96354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (N > 0) {
96454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            LOGV("Parcel %p looking for obj at %d, hint=%d\n",
96554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                 this, DPOS, opos);
96654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
96754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // Start at the current hint position, looking for an object at
96854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // the current data position.
96954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (opos < N) {
97054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                while (opos < (N-1) && OBJS[opos] < DPOS) {
97154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    opos++;
97254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                }
97354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            } else {
97454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                opos = N-1;
97554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
97654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (OBJS[opos] == DPOS) {
97754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                // Found it!
97854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGV("Parcel found obj %d at index %d with forward search",
97954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                     this, DPOS, opos);
98054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mNextObjectHint = opos+1;
98154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGV("readObject Setting data pos of %p to %d\n", this, mDataPos);
98254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return obj;
98354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
98454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
98554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // Look backwards for it...
98654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            while (opos > 0 && OBJS[opos] > DPOS) {
98754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                opos--;
98854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
98954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (OBJS[opos] == DPOS) {
99054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                // Found it!
99154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGV("Parcel found obj %d at index %d with backward search",
99254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                     this, DPOS, opos);
99354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mNextObjectHint = opos+1;
99454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGV("readObject Setting data pos of %p to %d\n", this, mDataPos);
99554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return obj;
99654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
99754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
99854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGW("Attempt to read object from Parcel %p at offset %d that is not in the object list",
99954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project             this, DPOS);
100054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
100154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NULL;
100254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
100354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
100454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::closeFileDescriptors()
100554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
100654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t i = mObjectsSize;
100754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (i > 0) {
100854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        //LOGI("Closing file descriptors for %d objects...", mObjectsSize);
100954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
101054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    while (i > 0) {
101154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        i--;
101254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const flat_binder_object* flat
101354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            = reinterpret_cast<flat_binder_object*>(mData+mObjects[i]);
101454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (flat->type == BINDER_TYPE_FD) {
101554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            //LOGI("Closing fd: %ld\n", flat->handle);
101654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            close(flat->handle);
101754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
101854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
101954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
102054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
102154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst uint8_t* Parcel::ipcData() const
102254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
102354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mData;
102454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
102554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
102654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::ipcDataSize() const
102754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
102854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return (mDataSize > mDataPos ? mDataSize : mDataPos);
102954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
103054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
103154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectconst size_t* Parcel::ipcObjects() const
103254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
103354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mObjects;
103454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
103554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
103654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectsize_t Parcel::ipcObjectsCount() const
103754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
103854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return mObjectsSize;
103954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
104054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
104154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::ipcSetDataReference(const uint8_t* data, size_t dataSize,
104254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const size_t* objects, size_t objectsCount, release_func relFunc, void* relCookie)
104354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
104454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    freeDataNoInit();
104554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mError = NO_ERROR;
104654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mData = const_cast<uint8_t*>(data);
104754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataSize = mDataCapacity = dataSize;
104854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    //LOGI("setDataReference Setting data size of %p to %lu (pid=%d)\n", this, mDataSize, getpid());
104954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataPos = 0;
105054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("setDataReference Setting data pos of %p to %d\n", this, mDataPos);
105154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjects = const_cast<size_t*>(objects);
105254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjectsSize = mObjectsCapacity = objectsCount;
105354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mNextObjectHint = 0;
105454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mOwner = relFunc;
105554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mOwnerCookie = relCookie;
105654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    scanForFds();
105754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
105854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
105954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::print(TextOutput& to, uint32_t flags) const
106054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
106154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    to << "Parcel(";
106254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
106354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (errorCheck() != NO_ERROR) {
106454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const status_t err = errorCheck();
106554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        to << "Error: " << (void*)err << " \"" << strerror(-err) << "\"";
106654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else if (dataSize() > 0) {
106754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const uint8_t* DATA = data();
106854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        to << indent << HexDump(DATA, dataSize()) << dedent;
106954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const size_t* OBJS = objects();
107054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const size_t N = objectsCount();
107154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        for (size_t i=0; i<N; i++) {
107254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const flat_binder_object* flat
107354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                = reinterpret_cast<const flat_binder_object*>(DATA+OBJS[i]);
107454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            to << endl << "Object #" << i << " @ " << (void*)OBJS[i] << ": "
107554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                << TypeCode(flat->type & 0x7f7f7f00)
107654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                << " = " << flat->binder;
107754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
107854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
107954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        to << "NULL";
108054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
108154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
108254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    to << ")";
108354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
108454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
108554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::releaseObjects()
108654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
108754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const sp<ProcessState> proc(ProcessState::self());
108854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t i = mObjectsSize;
108954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint8_t* const data = mData;
109054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t* const objects = mObjects;
109154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    while (i > 0) {
109254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        i--;
109354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const flat_binder_object* flat
109454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            = reinterpret_cast<flat_binder_object*>(data+objects[i]);
109554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        release_object(proc, *flat, this);
109654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
109754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
109854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
109954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::acquireObjects()
110054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
110154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    const sp<ProcessState> proc(ProcessState::self());
110254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t i = mObjectsSize;
110354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint8_t* const data = mData;
110454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t* const objects = mObjects;
110554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    while (i > 0) {
110654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        i--;
110754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const flat_binder_object* flat
110854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            = reinterpret_cast<flat_binder_object*>(data+objects[i]);
110954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        acquire_object(proc, *flat, this);
111054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
111154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
111254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
111354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::freeData()
111454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
111554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    freeDataNoInit();
111654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    initState();
111754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
111854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
111954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::freeDataNoInit()
112054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
112154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (mOwner) {
112254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        //LOGI("Freeing data ref of %p (pid=%d)\n", this, getpid());
112354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mOwner(this, mData, mDataSize, mObjects, mObjectsSize, mOwnerCookie);
112454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
112554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        releaseObjects();
112654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (mData) free(mData);
112754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (mObjects) free(mObjects);
112854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
112954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
113054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
113154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::growData(size_t len)
113254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
113354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t newSize = ((mDataSize+len)*3)/2;
113454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return (newSize <= mDataSize)
113554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            ? (status_t) NO_MEMORY
113654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            : continueWrite(newSize);
113754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
113854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
113954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::restartWrite(size_t desired)
114054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
114154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (mOwner) {
114254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        freeData();
114354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return continueWrite(desired);
114454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
114554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
114654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    uint8_t* data = (uint8_t*)realloc(mData, desired);
114754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (!data && desired > mDataCapacity) {
114854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mError = NO_MEMORY;
114954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        return NO_MEMORY;
115054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
115154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
115254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    releaseObjects();
115354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
115454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (data) {
115554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mData = data;
115654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataCapacity = desired;
115754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
115854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
115954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataSize = mDataPos = 0;
116054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("restartWrite Setting data size of %p to %d\n", this, mDataSize);
116154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("restartWrite Setting data pos of %p to %d\n", this, mDataPos);
116254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
116354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    free(mObjects);
116454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjects = NULL;
116554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjectsSize = mObjectsCapacity = 0;
116654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mNextObjectHint = 0;
116754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mHasFds = false;
116854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mFdsKnown = true;
116954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
117054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
117154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
117254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
117354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectstatus_t Parcel::continueWrite(size_t desired)
117454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
117554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // If shrinking, first adjust for any objects that appear
117654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    // after the new data size.
117754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    size_t objectsSize = mObjectsSize;
117854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (desired < mDataSize) {
117954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (desired == 0) {
118054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            objectsSize = 0;
118154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        } else {
118254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            while (objectsSize > 0) {
118354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                if (mObjects[objectsSize-1] < desired)
118454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    break;
118554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                objectsSize--;
118654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
118754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
118854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
118954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
119054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    if (mOwner) {
119154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // If the size is going to zero, just release the owner's data.
119254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (desired == 0) {
119354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            freeData();
119454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return NO_ERROR;
119554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
119654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
119754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // If there is a different owner, we need to take
119854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // posession.
119954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        uint8_t* data = (uint8_t*)malloc(desired);
120054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (!data) {
120154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mError = NO_MEMORY;
120254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return NO_MEMORY;
120354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
120454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        size_t* objects = NULL;
120554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
120654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (objectsSize) {
120754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            objects = (size_t*)malloc(objectsSize*sizeof(size_t));
120854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (!objects) {
120954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mError = NO_MEMORY;
121054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return NO_MEMORY;
121154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
121254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
121354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // Little hack to only acquire references on objects
121454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // we will be keeping.
121554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            size_t oldObjectsSize = mObjectsSize;
121654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsSize = objectsSize;
121754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            acquireObjects();
121854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsSize = oldObjectsSize;
121954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
122054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
122154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (mData) {
122254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            memcpy(data, mData, mDataSize < desired ? mDataSize : desired);
122354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
122454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (objects && mObjects) {
122554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            memcpy(objects, mObjects, objectsSize*sizeof(size_t));
122654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
122754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        //LOGI("Freeing data ref of %p (pid=%d)\n", this, getpid());
122854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mOwner(this, mData, mDataSize, mObjects, mObjectsSize, mOwnerCookie);
122954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mOwner = NULL;
123054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
123154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mData = data;
123254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mObjects = objects;
123354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataSize = (mDataSize < desired) ? mDataSize : desired;
123454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize);
123554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataCapacity = desired;
123654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mObjectsSize = mObjectsCapacity = objectsSize;
123754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mNextObjectHint = 0;
123854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
123954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else if (mData) {
124054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (objectsSize < mObjectsSize) {
124154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            // Need to release refs on any objects we are dropping.
124254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            const sp<ProcessState> proc(ProcessState::self());
124354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            for (size_t i=objectsSize; i<mObjectsSize; i++) {
124454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                const flat_binder_object* flat
124554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    = reinterpret_cast<flat_binder_object*>(mData+mObjects[i]);
124654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                if (flat->type == BINDER_TYPE_FD) {
124754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    // will need to rescan because we may have lopped off the only FDs
124854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                    mFdsKnown = false;
124954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                }
125054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                release_object(proc, *flat, this);
125154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
125254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            size_t* objects =
125354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                (size_t*)realloc(mObjects, objectsSize*sizeof(size_t));
125454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (objects) {
125554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mObjects = objects;
125654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
125754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mObjectsSize = objectsSize;
125854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mNextObjectHint = 0;
125954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
126054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
126154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // We own the data, so we can just do a realloc().
126254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (desired > mDataCapacity) {
126354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            uint8_t* data = (uint8_t*)realloc(mData, desired);
126454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (data) {
126554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mData = data;
126654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mDataCapacity = desired;
126754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            } else if (desired > mDataCapacity) {
126854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mError = NO_MEMORY;
126954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                return NO_MEMORY;
127054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
127154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        } else {
127254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mDataSize = desired;
127354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            LOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize);
127454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            if (mDataPos > desired) {
127554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                mDataPos = desired;
127654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project                LOGV("continueWrite Setting data pos of %p to %d\n", this, mDataPos);
127754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            }
127854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
127954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
128054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    } else {
128154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        // This is the first data.  Easy!
128254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        uint8_t* data = (uint8_t*)malloc(desired);
128354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (!data) {
128454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            mError = NO_MEMORY;
128554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            return NO_MEMORY;
128654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
128754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
128854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if(!(mDataCapacity == 0 && mObjects == NULL
128954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project             && mObjectsCapacity == 0)) {
129054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            LOGE("continueWrite: %d/%p/%d/%d", mDataCapacity, mObjects, mObjectsCapacity, desired);
129154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
129254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
129354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mData = data;
129454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataSize = mDataPos = 0;
129554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize);
129654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        LOGV("continueWrite Setting data pos of %p to %d\n", this, mDataPos);
129754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        mDataCapacity = desired;
129854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
129954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
130054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    return NO_ERROR;
130154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
130254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
130354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::initState()
130454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
130554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mError = NO_ERROR;
130654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mData = 0;
130754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataSize = 0;
130854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataCapacity = 0;
130954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mDataPos = 0;
131054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("initState Setting data size of %p to %d\n", this, mDataSize);
131154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    LOGV("initState Setting data pos of %p to %d\n", this, mDataPos);
131254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjects = NULL;
131354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjectsSize = 0;
131454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mObjectsCapacity = 0;
131554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mNextObjectHint = 0;
131654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mHasFds = false;
131754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mFdsKnown = true;
131854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mOwner = NULL;
131954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
132054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
132154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Projectvoid Parcel::scanForFds() const
132254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project{
132354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    bool hasFds = false;
132454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    for (size_t i=0; i<mObjectsSize; i++) {
132554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        const flat_binder_object* flat
132654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            = reinterpret_cast<const flat_binder_object*>(mData + mObjects[i]);
132754b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        if (flat->type == BINDER_TYPE_FD) {
132854b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            hasFds = true;
132954b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project            break;
133054b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project        }
133154b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    }
133254b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mHasFds = hasFds;
133354b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project    mFdsKnown = true;
133454b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}
133554b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project
133654b6cfa9a9e5b861a9930af873580d6dc20f773The Android Open Source Project}; // namespace android
1337