diff options
Diffstat (limited to 'libs/binder')
-rw-r--r-- | libs/binder/Android.mk | 15 | ||||
-rw-r--r-- | libs/binder/Binder.cpp | 44 | ||||
-rw-r--r-- | libs/binder/BpBinder.cpp | 16 | ||||
-rw-r--r-- | libs/binder/Debug.cpp | 2 | ||||
-rw-r--r-- | libs/binder/IAppOpsCallback.cpp | 1 | ||||
-rw-r--r-- | libs/binder/IAppOpsService.cpp | 1 | ||||
-rw-r--r-- | libs/binder/IBatteryStats.cpp | 163 | ||||
-rw-r--r-- | libs/binder/IMemory.cpp | 14 | ||||
-rw-r--r-- | libs/binder/IPCThreadState.cpp | 110 | ||||
-rw-r--r-- | libs/binder/IPermissionController.cpp | 1 | ||||
-rw-r--r-- | libs/binder/IServiceManager.cpp | 1 | ||||
-rw-r--r-- | libs/binder/MemoryDealer.cpp | 10 | ||||
-rw-r--r-- | libs/binder/Parcel.cpp | 368 | ||||
-rw-r--r-- | libs/binder/ProcessState.cpp | 39 |
14 files changed, 524 insertions, 261 deletions
diff --git a/libs/binder/Android.mk b/libs/binder/Android.mk index f3f8daf..79decfe 100644 --- a/libs/binder/Android.mk +++ b/libs/binder/Android.mk @@ -21,6 +21,7 @@ sources := \ Debug.cpp \ IAppOpsCallback.cpp \ IAppOpsService.cpp \ + IBatteryStats.cpp \ IInterface.cpp \ IMemory.cpp \ IPCThreadState.cpp \ @@ -38,15 +39,25 @@ sources := \ LOCAL_PATH:= $(call my-dir) include $(CLEAR_VARS) -LOCAL_LDLIBS += -lpthread LOCAL_MODULE := libbinder LOCAL_SHARED_LIBRARIES := liblog libcutils libutils LOCAL_SRC_FILES := $(sources) +ifneq ($(TARGET_USES_64_BIT_BINDER),true) +ifneq ($(TARGET_IS_64_BIT),true) +LOCAL_CFLAGS += -DBINDER_IPC_32BIT=1 +endif +endif +LOCAL_CFLAGS += -Werror include $(BUILD_SHARED_LIBRARY) include $(CLEAR_VARS) -LOCAL_LDLIBS += -lpthread LOCAL_MODULE := libbinder LOCAL_STATIC_LIBRARIES += libutils LOCAL_SRC_FILES := $(sources) +ifneq ($(TARGET_USES_64_BIT_BINDER),true) +ifneq ($(TARGET_IS_64_BIT),true) +LOCAL_CFLAGS += -DBINDER_IPC_32BIT=1 +endif +endif +LOCAL_CFLAGS += -Werror include $(BUILD_STATIC_LIBRARY) diff --git a/libs/binder/Binder.cpp b/libs/binder/Binder.cpp index 1f21f9c..2554351 100644 --- a/libs/binder/Binder.cpp +++ b/libs/binder/Binder.cpp @@ -16,7 +16,7 @@ #include <binder/Binder.h> -#include <utils/Atomic.h> +#include <stdatomic.h> #include <utils/misc.h> #include <binder/BpBinder.h> #include <binder/IInterface.h> @@ -39,7 +39,7 @@ IBinder::~IBinder() // --------------------------------------------------------------------------- -sp<IInterface> IBinder::queryLocalInterface(const String16& descriptor) +sp<IInterface> IBinder::queryLocalInterface(const String16& /*descriptor*/) { return NULL; } @@ -71,8 +71,8 @@ public: // --------------------------------------------------------------------------- BBinder::BBinder() - : mExtras(NULL) { + atomic_init(&mExtras, 0); } bool BBinder::isBinderAlive() const @@ -117,19 +117,20 @@ status_t BBinder::transact( } status_t BBinder::linkToDeath( - const sp<DeathRecipient>& recipient, void* cookie, uint32_t flags) + const sp<DeathRecipient>& /*recipient*/, void* /*cookie*/, + uint32_t /*flags*/) { return INVALID_OPERATION; } status_t BBinder::unlinkToDeath( - const wp<DeathRecipient>& recipient, void* cookie, uint32_t flags, - wp<DeathRecipient>* outRecipient) + const wp<DeathRecipient>& /*recipient*/, void* /*cookie*/, + uint32_t /*flags*/, wp<DeathRecipient>* /*outRecipient*/) { return INVALID_OPERATION; } -status_t BBinder::dump(int fd, const Vector<String16>& args) + status_t BBinder::dump(int /*fd*/, const Vector<String16>& /*args*/) { return NO_ERROR; } @@ -138,14 +139,19 @@ void BBinder::attachObject( const void* objectID, void* object, void* cleanupCookie, object_cleanup_func func) { - Extras* e = mExtras; + Extras* e = reinterpret_cast<Extras*>( + atomic_load_explicit(&mExtras, memory_order_acquire)); if (!e) { e = new Extras; - if (android_atomic_cmpxchg(0, reinterpret_cast<int32_t>(e), - reinterpret_cast<volatile int32_t*>(&mExtras)) != 0) { + uintptr_t expected = 0; + if (!atomic_compare_exchange_strong_explicit( + &mExtras, &expected, + reinterpret_cast<uintptr_t>(e), + memory_order_release, + memory_order_acquire)) { delete e; - e = mExtras; + e = reinterpret_cast<Extras*>(expected); // Filled in by CAS } if (e == 0) return; // out of memory } @@ -156,7 +162,8 @@ void BBinder::attachObject( void* BBinder::findObject(const void* objectID) const { - Extras* e = mExtras; + Extras* e = reinterpret_cast<Extras*>( + atomic_load_explicit(&mExtras, memory_order_acquire)); if (!e) return NULL; AutoMutex _l(e->mLock); @@ -165,7 +172,8 @@ void* BBinder::findObject(const void* objectID) const void BBinder::detachObject(const void* objectID) { - Extras* e = mExtras; + Extras* e = reinterpret_cast<Extras*>( + atomic_load_explicit(&mExtras, memory_order_acquire)); if (!e) return; AutoMutex _l(e->mLock); @@ -179,12 +187,14 @@ BBinder* BBinder::localBinder() BBinder::~BBinder() { - if (mExtras) delete mExtras; + Extras* e = reinterpret_cast<Extras*>( + atomic_load_explicit(&mExtras, memory_order_relaxed)); + if (e) delete e; } status_t BBinder::onTransact( - uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) + uint32_t code, const Parcel& data, Parcel* reply, uint32_t /*flags*/) { switch (code) { case INTERFACE_TRANSACTION: @@ -246,14 +256,14 @@ void BpRefBase::onFirstRef() android_atomic_or(kRemoteAcquired, &mState); } -void BpRefBase::onLastStrongRef(const void* id) +void BpRefBase::onLastStrongRef(const void* /*id*/) { if (mRemote) { mRemote->decStrong(this); } } -bool BpRefBase::onIncStrongAttempted(uint32_t flags, const void* id) +bool BpRefBase::onIncStrongAttempted(uint32_t /*flags*/, const void* /*id*/) { return mRemote ? mRefs->attemptIncStrong(this) : false; } diff --git a/libs/binder/BpBinder.cpp b/libs/binder/BpBinder.cpp index 47a62db..101de7e 100644 --- a/libs/binder/BpBinder.cpp +++ b/libs/binder/BpBinder.cpp @@ -73,7 +73,7 @@ void BpBinder::ObjectManager::detach(const void* objectID) void BpBinder::ObjectManager::kill() { const size_t N = mObjects.size(); - ALOGV("Killing %d objects in manager %p", N, this); + ALOGV("Killing %zu objects in manager %p", N, this); for (size_t i=0; i<N; i++) { const entry_t& e = mObjects.valueAt(i); if (e.func != NULL) { @@ -119,11 +119,11 @@ const String16& BpBinder::getInterfaceDescriptor() const mDescriptorCache = res; } } - + // we're returning a reference to a non-static object here. Usually this - // is not something smart to do, however, with binder objects it is + // is not something smart to do, however, with binder objects it is // (usually) safe because they are reference-counted. - + return mDescriptorCache; } @@ -260,8 +260,8 @@ void BpBinder::sendObituary() mObitsSent = 1; mLock.unlock(); - ALOGV("Reporting death of proxy %p for %d recipients\n", - this, obits ? obits->size() : 0); + ALOGV("Reporting death of proxy %p for %zu recipients\n", + this, obits ? obits->size() : 0U); if (obits != NULL) { const size_t N = obits->size(); @@ -343,7 +343,7 @@ void BpBinder::onFirstRef() if (ipc) ipc->incStrongHandle(mHandle); } -void BpBinder::onLastStrongRef(const void* id) +void BpBinder::onLastStrongRef(const void* /*id*/) { ALOGV("onLastStrongRef BpBinder %p handle %d\n", this, mHandle); IF_ALOGV() { @@ -353,7 +353,7 @@ void BpBinder::onLastStrongRef(const void* id) if (ipc) ipc->decStrongHandle(mHandle); } -bool BpBinder::onIncStrongAttempted(uint32_t flags, const void* id) +bool BpBinder::onIncStrongAttempted(uint32_t /*flags*/, const void* /*id*/) { ALOGV("onIncStrongAttempted BpBinder %p handle %d\n", this, mHandle); IPCThreadState* ipc = IPCThreadState::self(); diff --git a/libs/binder/Debug.cpp b/libs/binder/Debug.cpp index a8b6e83..0ffafbb 100644 --- a/libs/binder/Debug.cpp +++ b/libs/binder/Debug.cpp @@ -38,7 +38,7 @@ const char* stringForIndent(int32_t indentLevel) // --------------------------------------------------------------------- -static void defaultPrintFunc(void* cookie, const char* txt) +static void defaultPrintFunc(void* /*cookie*/, const char* txt) { printf("%s", txt); } diff --git a/libs/binder/IAppOpsCallback.cpp b/libs/binder/IAppOpsCallback.cpp index e0aad23..2aaf566 100644 --- a/libs/binder/IAppOpsCallback.cpp +++ b/libs/binder/IAppOpsCallback.cpp @@ -18,7 +18,6 @@ #include <binder/IAppOpsCallback.h> -#include <utils/Debug.h> #include <utils/Log.h> #include <binder/Parcel.h> #include <utils/String8.h> diff --git a/libs/binder/IAppOpsService.cpp b/libs/binder/IAppOpsService.cpp index 471e3e9..f58a352 100644 --- a/libs/binder/IAppOpsService.cpp +++ b/libs/binder/IAppOpsService.cpp @@ -18,7 +18,6 @@ #include <binder/IAppOpsService.h> -#include <utils/Debug.h> #include <utils/Log.h> #include <binder/Parcel.h> #include <utils/String8.h> diff --git a/libs/binder/IBatteryStats.cpp b/libs/binder/IBatteryStats.cpp new file mode 100644 index 0000000..8f3b7b4 --- /dev/null +++ b/libs/binder/IBatteryStats.cpp @@ -0,0 +1,163 @@ +/* + * Copyright (C) 2013 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <binder/IBatteryStats.h> + +#include <utils/Log.h> +#include <binder/Parcel.h> +#include <utils/String8.h> + +#include <private/binder/Static.h> + +namespace android { + +// ---------------------------------------------------------------------- + +class BpBatteryStats : public BpInterface<IBatteryStats> +{ +public: + BpBatteryStats(const sp<IBinder>& impl) + : BpInterface<IBatteryStats>(impl) + { + } + + virtual void noteStartSensor(int uid, int sensor) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + data.writeInt32(sensor); + remote()->transact(NOTE_START_SENSOR_TRANSACTION, data, &reply); + } + + virtual void noteStopSensor(int uid, int sensor) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + data.writeInt32(sensor); + remote()->transact(NOTE_STOP_SENSOR_TRANSACTION, data, &reply); + } + + virtual void noteStartVideo(int uid) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + remote()->transact(NOTE_START_VIDEO_TRANSACTION, data, &reply); + } + + virtual void noteStopVideo(int uid) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + remote()->transact(NOTE_STOP_VIDEO_TRANSACTION, data, &reply); + } + + virtual void noteStartAudio(int uid) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + remote()->transact(NOTE_START_AUDIO_TRANSACTION, data, &reply); + } + + virtual void noteStopAudio(int uid) { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + data.writeInt32(uid); + remote()->transact(NOTE_STOP_AUDIO_TRANSACTION, data, &reply); + } + + virtual void noteResetVideo() { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + remote()->transact(NOTE_RESET_VIDEO_TRANSACTION, data, &reply); + } + + virtual void noteResetAudio() { + Parcel data, reply; + data.writeInterfaceToken(IBatteryStats::getInterfaceDescriptor()); + remote()->transact(NOTE_RESET_AUDIO_TRANSACTION, data, &reply); + } +}; + +IMPLEMENT_META_INTERFACE(BatteryStats, "com.android.internal.app.IBatteryStats"); + +// ---------------------------------------------------------------------- + +status_t BnBatteryStats::onTransact( + uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) +{ + switch(code) { + case NOTE_START_SENSOR_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + int sensor = data.readInt32(); + noteStartSensor(uid, sensor); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_STOP_SENSOR_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + int sensor = data.readInt32(); + noteStopSensor(uid, sensor); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_START_VIDEO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + noteStartVideo(uid); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_STOP_VIDEO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + noteStopVideo(uid); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_START_AUDIO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + noteStartAudio(uid); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_STOP_AUDIO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + int uid = data.readInt32(); + noteStopAudio(uid); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_RESET_VIDEO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + noteResetVideo(); + reply->writeNoException(); + return NO_ERROR; + } break; + case NOTE_RESET_AUDIO_TRANSACTION: { + CHECK_INTERFACE(IBatteryStats, data, reply); + noteResetAudio(); + reply->writeNoException(); + return NO_ERROR; + } break; + default: + return BBinder::onTransact(code, data, reply, flags); + } +} + +}; // namespace android diff --git a/libs/binder/IMemory.cpp b/libs/binder/IMemory.cpp index 07cb41a..d8ed995 100644 --- a/libs/binder/IMemory.cpp +++ b/libs/binder/IMemory.cpp @@ -244,7 +244,7 @@ BpMemoryHeap::~BpMemoryHeap() { sp<IBinder> binder = const_cast<BpMemoryHeap*>(this)->asBinder(); if (VERBOSE) { - ALOGD("UNMAPPING binder=%p, heap=%p, size=%d, fd=%d", + ALOGD("UNMAPPING binder=%p, heap=%p, size=%zu, fd=%d", binder.get(), this, mSize, mHeapId); CallStack stack(LOG_TAG); } @@ -296,11 +296,11 @@ void BpMemoryHeap::assertReallyMapped() const uint32_t flags = reply.readInt32(); uint32_t offset = reply.readInt32(); - ALOGE_IF(err, "binder=%p transaction failed fd=%d, size=%ld, err=%d (%s)", + ALOGE_IF(err, "binder=%p transaction failed fd=%d, size=%zd, err=%d (%s)", asBinder().get(), parcel_fd, size, err, strerror(-err)); int fd = dup( parcel_fd ); - ALOGE_IF(fd==-1, "cannot dup fd=%d, size=%ld, err=%d (%s)", + ALOGE_IF(fd==-1, "cannot dup fd=%d, size=%zd, err=%d (%s)", parcel_fd, size, err, strerror(errno)); int access = PROT_READ; @@ -313,7 +313,7 @@ void BpMemoryHeap::assertReallyMapped() const mRealHeap = true; mBase = mmap(0, size, access, MAP_SHARED, fd, offset); if (mBase == MAP_FAILED) { - ALOGE("cannot map BpMemoryHeap (binder=%p), size=%ld, fd=%d (%s)", + ALOGE("cannot map BpMemoryHeap (binder=%p), size=%zd, fd=%d (%s)", asBinder().get(), size, fd, strerror(errno)); close(fd); } else { @@ -402,7 +402,7 @@ sp<IMemoryHeap> HeapCache::find_heap(const sp<IBinder>& binder) if (i>=0) { heap_info_t& info = mHeapCache.editValueAt(i); ALOGD_IF(VERBOSE, - "found binder=%p, heap=%p, size=%d, fd=%d, count=%d", + "found binder=%p, heap=%p, size=%zu, fd=%d, count=%d", binder.get(), info.heap.get(), static_cast<BpMemoryHeap*>(info.heap.get())->mSize, static_cast<BpMemoryHeap*>(info.heap.get())->mHeapId, @@ -435,7 +435,7 @@ void HeapCache::free_heap(const wp<IBinder>& binder) int32_t c = android_atomic_dec(&info.count); if (c == 1) { ALOGD_IF(VERBOSE, - "removing binder=%p, heap=%p, size=%d, fd=%d, count=%d", + "removing binder=%p, heap=%p, size=%zu, fd=%d, count=%d", binder.unsafe_get(), info.heap.get(), static_cast<BpMemoryHeap*>(info.heap.get())->mSize, static_cast<BpMemoryHeap*>(info.heap.get())->mHeapId, @@ -466,7 +466,7 @@ void HeapCache::dump_heaps() for (int i=0 ; i<c ; i++) { const heap_info_t& info = mHeapCache.valueAt(i); BpMemoryHeap const* h(static_cast<BpMemoryHeap const *>(info.heap.get())); - ALOGD("hey=%p, heap=%p, count=%d, (fd=%d, base=%p, size=%d)", + ALOGD("hey=%p, heap=%p, count=%d, (fd=%d, base=%p, size=%zu)", mHeapCache.keyAt(i).unsafe_get(), info.heap.get(), info.count, h->mHeapId, h->mBase, h->mSize); diff --git a/libs/binder/IPCThreadState.cpp b/libs/binder/IPCThreadState.cpp index 5951a3f..dd04dcf 100644 --- a/libs/binder/IPCThreadState.cpp +++ b/libs/binder/IPCThreadState.cpp @@ -23,7 +23,6 @@ #include <binder/TextOutput.h> #include <cutils/sched_policy.h> -#include <utils/Debug.h> #include <utils/Log.h> #include <utils/threads.h> @@ -533,7 +532,7 @@ status_t IPCThreadState::handlePolledCommands() return result; } -void IPCThreadState::stopProcess(bool immediate) +void IPCThreadState::stopProcess(bool /*immediate*/) { //ALOGI("**** STOPPING PROCESS"); flushCommands(); @@ -635,6 +634,7 @@ void IPCThreadState::decWeakHandle(int32_t handle) status_t IPCThreadState::attemptIncStrongHandle(int32_t handle) { +#if HAS_BC_ATTEMPT_ACQUIRE LOG_REMOTEREFS("IPCThreadState::attemptIncStrongHandle(%d)\n", handle); mOut.writeInt32(BC_ATTEMPT_ACQUIRE); mOut.writeInt32(0); // xxx was thread priority @@ -649,6 +649,11 @@ status_t IPCThreadState::attemptIncStrongHandle(int32_t handle) #endif return result; +#else + (void)handle; + ALOGE("%s(%d): Not supported\n", __func__, handle); + return INVALID_OPERATION; +#endif } void IPCThreadState::expungeHandle(int32_t handle, IBinder* binder) @@ -663,7 +668,7 @@ status_t IPCThreadState::requestDeathNotification(int32_t handle, BpBinder* prox { mOut.writeInt32(BC_REQUEST_DEATH_NOTIFICATION); mOut.writeInt32((int32_t)handle); - mOut.writeInt32((int32_t)proxy); + mOut.writePointer((uintptr_t)proxy); return NO_ERROR; } @@ -671,7 +676,7 @@ status_t IPCThreadState::clearDeathNotification(int32_t handle, BpBinder* proxy) { mOut.writeInt32(BC_CLEAR_DEATH_NOTIFICATION); mOut.writeInt32((int32_t)handle); - mOut.writeInt32((int32_t)proxy); + mOut.writePointer((uintptr_t)proxy); return NO_ERROR; } @@ -753,23 +758,23 @@ status_t IPCThreadState::waitForResponse(Parcel *reply, status_t *acquireResult) reply->ipcSetDataReference( reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), tr.data_size, - reinterpret_cast<const size_t*>(tr.data.ptr.offsets), - tr.offsets_size/sizeof(size_t), + reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets), + tr.offsets_size/sizeof(binder_size_t), freeBuffer, this); } else { - err = *static_cast<const status_t*>(tr.data.ptr.buffer); + err = *reinterpret_cast<const status_t*>(tr.data.ptr.buffer); freeBuffer(NULL, reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), tr.data_size, - reinterpret_cast<const size_t*>(tr.data.ptr.offsets), - tr.offsets_size/sizeof(size_t), this); + reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets), + tr.offsets_size/sizeof(binder_size_t), this); } } else { freeBuffer(NULL, reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), tr.data_size, - reinterpret_cast<const size_t*>(tr.data.ptr.offsets), - tr.offsets_size/sizeof(size_t), this); + reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets), + tr.offsets_size/sizeof(binder_size_t), this); continue; } } @@ -809,12 +814,12 @@ status_t IPCThreadState::talkWithDriver(bool doReceive) const size_t outAvail = (!doReceive || needRead) ? mOut.dataSize() : 0; bwr.write_size = outAvail; - bwr.write_buffer = (long unsigned int)mOut.data(); + bwr.write_buffer = (uintptr_t)mOut.data(); // This is what we'll read. if (doReceive && needRead) { bwr.read_size = mIn.dataCapacity(); - bwr.read_buffer = (long unsigned int)mIn.data(); + bwr.read_buffer = (uintptr_t)mIn.data(); } else { bwr.read_size = 0; bwr.read_buffer = 0; @@ -861,14 +866,14 @@ status_t IPCThreadState::talkWithDriver(bool doReceive) } while (err == -EINTR); IF_LOG_COMMANDS() { - alog << "Our err: " << (void*)err << ", write consumed: " + alog << "Our err: " << (void*)(intptr_t)err << ", write consumed: " << bwr.write_consumed << " (of " << mOut.dataSize() << "), read consumed: " << bwr.read_consumed << endl; } if (err >= NO_ERROR) { if (bwr.write_consumed > 0) { - if (bwr.write_consumed < (ssize_t)mOut.dataSize()) + if (bwr.write_consumed < mOut.dataSize()) mOut.remove(0, bwr.write_consumed); else mOut.setDataSize(0); @@ -898,6 +903,7 @@ status_t IPCThreadState::writeTransactionData(int32_t cmd, uint32_t binderFlags, { binder_transaction_data tr; + tr.target.ptr = 0; /* Don't pass uninitialized stack data to a remote process */ tr.target.handle = handle; tr.code = code; tr.flags = binderFlags; @@ -909,15 +915,15 @@ status_t IPCThreadState::writeTransactionData(int32_t cmd, uint32_t binderFlags, if (err == NO_ERROR) { tr.data_size = data.ipcDataSize(); tr.data.ptr.buffer = data.ipcData(); - tr.offsets_size = data.ipcObjectsCount()*sizeof(size_t); + tr.offsets_size = data.ipcObjectsCount()*sizeof(binder_size_t); tr.data.ptr.offsets = data.ipcObjects(); } else if (statusBuffer) { tr.flags |= TF_STATUS_CODE; *statusBuffer = err; tr.data_size = sizeof(status_t); - tr.data.ptr.buffer = statusBuffer; + tr.data.ptr.buffer = reinterpret_cast<uintptr_t>(statusBuffer); tr.offsets_size = 0; - tr.data.ptr.offsets = NULL; + tr.data.ptr.offsets = 0; } else { return (mLastError = err); } @@ -950,8 +956,8 @@ status_t IPCThreadState::executeCommand(int32_t cmd) break; case BR_ACQUIRE: - refs = (RefBase::weakref_type*)mIn.readInt32(); - obj = (BBinder*)mIn.readInt32(); + refs = (RefBase::weakref_type*)mIn.readPointer(); + obj = (BBinder*)mIn.readPointer(); ALOG_ASSERT(refs->refBase() == obj, "BR_ACQUIRE: object %p does not match cookie %p (expected %p)", refs, obj, refs->refBase()); @@ -961,13 +967,13 @@ status_t IPCThreadState::executeCommand(int32_t cmd) obj->printRefs(); } mOut.writeInt32(BC_ACQUIRE_DONE); - mOut.writeInt32((int32_t)refs); - mOut.writeInt32((int32_t)obj); + mOut.writePointer((uintptr_t)refs); + mOut.writePointer((uintptr_t)obj); break; case BR_RELEASE: - refs = (RefBase::weakref_type*)mIn.readInt32(); - obj = (BBinder*)mIn.readInt32(); + refs = (RefBase::weakref_type*)mIn.readPointer(); + obj = (BBinder*)mIn.readPointer(); ALOG_ASSERT(refs->refBase() == obj, "BR_RELEASE: object %p does not match cookie %p (expected %p)", refs, obj, refs->refBase()); @@ -979,17 +985,17 @@ status_t IPCThreadState::executeCommand(int32_t cmd) break; case BR_INCREFS: - refs = (RefBase::weakref_type*)mIn.readInt32(); - obj = (BBinder*)mIn.readInt32(); + refs = (RefBase::weakref_type*)mIn.readPointer(); + obj = (BBinder*)mIn.readPointer(); refs->incWeak(mProcess.get()); mOut.writeInt32(BC_INCREFS_DONE); - mOut.writeInt32((int32_t)refs); - mOut.writeInt32((int32_t)obj); + mOut.writePointer((uintptr_t)refs); + mOut.writePointer((uintptr_t)obj); break; case BR_DECREFS: - refs = (RefBase::weakref_type*)mIn.readInt32(); - obj = (BBinder*)mIn.readInt32(); + refs = (RefBase::weakref_type*)mIn.readPointer(); + obj = (BBinder*)mIn.readPointer(); // NOTE: This assertion is not valid, because the object may no // longer exist (thus the (BBinder*)cast above resulting in a different // memory address). @@ -1000,8 +1006,8 @@ status_t IPCThreadState::executeCommand(int32_t cmd) break; case BR_ATTEMPT_ACQUIRE: - refs = (RefBase::weakref_type*)mIn.readInt32(); - obj = (BBinder*)mIn.readInt32(); + refs = (RefBase::weakref_type*)mIn.readPointer(); + obj = (BBinder*)mIn.readPointer(); { const bool success = refs->attemptIncStrong(mProcess.get()); @@ -1026,15 +1032,18 @@ status_t IPCThreadState::executeCommand(int32_t cmd) buffer.ipcSetDataReference( reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), tr.data_size, - reinterpret_cast<const size_t*>(tr.data.ptr.offsets), - tr.offsets_size/sizeof(size_t), freeBuffer, this); + reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets), + tr.offsets_size/sizeof(binder_size_t), freeBuffer, this); const pid_t origPid = mCallingPid; const uid_t origUid = mCallingUid; - + const int32_t origStrictModePolicy = mStrictModePolicy; + const int32_t origTransactionBinderFlags = mLastTransactionBinderFlags; + mCallingPid = tr.sender_pid; mCallingUid = tr.sender_euid; - + mLastTransactionBinderFlags = tr.flags; + int curPrio = getpriority(PRIO_PROCESS, mMyThreadId); if (gDisableBackgroundScheduling) { if (curPrio > ANDROID_PRIORITY_NORMAL) { @@ -1056,8 +1065,9 @@ status_t IPCThreadState::executeCommand(int32_t cmd) } //ALOGI(">>>> TRANSACT from pid %d uid %d\n", mCallingPid, mCallingUid); - + Parcel reply; + status_t error; IF_LOG_TRANSACTIONS() { TextOutput::Bundle _b(alog); alog << "BR_TRANSACTION thr " << (void*)pthread_self() @@ -1071,19 +1081,18 @@ status_t IPCThreadState::executeCommand(int32_t cmd) } if (tr.target.ptr) { sp<BBinder> b((BBinder*)tr.cookie); - const status_t error = b->transact(tr.code, buffer, &reply, tr.flags); - if (error < NO_ERROR) reply.setError(error); + error = b->transact(tr.code, buffer, &reply, tr.flags); } else { - const status_t error = the_context_object->transact(tr.code, buffer, &reply, tr.flags); - if (error < NO_ERROR) reply.setError(error); + error = the_context_object->transact(tr.code, buffer, &reply, tr.flags); } - + //ALOGI("<<<< TRANSACT from pid %d restore pid %d uid %d\n", // mCallingPid, origPid, origUid); if ((tr.flags & TF_ONE_WAY) == 0) { LOG_ONEWAY("Sending reply to %d!", mCallingPid); + if (error < NO_ERROR) reply.setError(error); sendReply(reply, 0); } else { LOG_ONEWAY("NOT sending reply to %d!", mCallingPid); @@ -1091,6 +1100,8 @@ status_t IPCThreadState::executeCommand(int32_t cmd) mCallingPid = origPid; mCallingUid = origUid; + mStrictModePolicy = origStrictModePolicy; + mLastTransactionBinderFlags = origTransactionBinderFlags; IF_LOG_TRANSACTIONS() { TextOutput::Bundle _b(alog); @@ -1103,15 +1114,15 @@ status_t IPCThreadState::executeCommand(int32_t cmd) case BR_DEAD_BINDER: { - BpBinder *proxy = (BpBinder*)mIn.readInt32(); + BpBinder *proxy = (BpBinder*)mIn.readPointer(); proxy->sendObituary(); mOut.writeInt32(BC_DEAD_BINDER_DONE); - mOut.writeInt32((int32_t)proxy); + mOut.writePointer((uintptr_t)proxy); } break; case BR_CLEAR_DEATH_NOTIFICATION_DONE: { - BpBinder *proxy = (BpBinder*)mIn.readInt32(); + BpBinder *proxy = (BpBinder*)mIn.readPointer(); proxy->getWeakRefs()->decWeak(proxy); } break; @@ -1154,9 +1165,10 @@ void IPCThreadState::threadDestructor(void *st) } -void IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data, size_t dataSize, - const size_t* objects, size_t objectsSize, - void* cookie) +void IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data, + size_t /*dataSize*/, + const binder_size_t* /*objects*/, + size_t /*objectsSize*/, void* /*cookie*/) { //ALOGI("Freeing parcel %p", &parcel); IF_LOG_COMMANDS() { @@ -1166,7 +1178,7 @@ void IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data, size_t data if (parcel != NULL) parcel->closeFileDescriptors(); IPCThreadState* state = self(); state->mOut.writeInt32(BC_FREE_BUFFER); - state->mOut.writeInt32((int32_t)data); + state->mOut.writePointer((uintptr_t)data); } }; // namespace android diff --git a/libs/binder/IPermissionController.cpp b/libs/binder/IPermissionController.cpp index e13036f..437113d 100644 --- a/libs/binder/IPermissionController.cpp +++ b/libs/binder/IPermissionController.cpp @@ -18,7 +18,6 @@ #include <binder/IPermissionController.h> -#include <utils/Debug.h> #include <utils/Log.h> #include <binder/Parcel.h> #include <utils/String8.h> diff --git a/libs/binder/IServiceManager.cpp b/libs/binder/IServiceManager.cpp index a341ca8..7b1b0e7 100644 --- a/libs/binder/IServiceManager.cpp +++ b/libs/binder/IServiceManager.cpp @@ -18,7 +18,6 @@ #include <binder/IServiceManager.h> -#include <utils/Debug.h> #include <utils/Log.h> #include <binder/IPCThreadState.h> #include <binder/Parcel.h> diff --git a/libs/binder/MemoryDealer.cpp b/libs/binder/MemoryDealer.cpp index 8d0e0a7..8739625 100644 --- a/libs/binder/MemoryDealer.cpp +++ b/libs/binder/MemoryDealer.cpp @@ -210,7 +210,7 @@ Allocation::~Allocation() #ifdef MADV_REMOVE if (size) { int err = madvise(start_ptr, size, MADV_REMOVE); - ALOGW_IF(err, "madvise(%p, %u, MADV_REMOVE) returned %s", + ALOGW_IF(err, "madvise(%p, %zu, MADV_REMOVE) returned %s", start_ptr, size, err<0 ? strerror(errno) : "Ok"); } #endif @@ -225,8 +225,8 @@ Allocation::~Allocation() // ---------------------------------------------------------------------------- -MemoryDealer::MemoryDealer(size_t size, const char* name) - : mHeap(new MemoryHeapBase(size, 0, name)), +MemoryDealer::MemoryDealer(size_t size, const char* name, uint32_t flags) + : mHeap(new MemoryHeapBase(size, flags, name)), mAllocator(new SimpleBestFitAllocator(size)) { } @@ -445,8 +445,8 @@ void SimpleBestFitAllocator::dump_l(String8& result, int np = ((cur->next) && cur->next->prev != cur) ? 1 : 0; int pn = ((cur->prev) && cur->prev->next != cur) ? 2 : 0; - snprintf(buffer, SIZE, " %3u: %08x | 0x%08X | 0x%08X | %s %s\n", - i, int(cur), int(cur->start*kMemoryAlign), + snprintf(buffer, SIZE, " %3u: %p | 0x%08X | 0x%08X | %s %s\n", + i, cur, int(cur->start*kMemoryAlign), int(cur->size*kMemoryAlign), int(cur->free) ? "F" : "A", errs[np|pn]); diff --git a/libs/binder/Parcel.cpp b/libs/binder/Parcel.cpp index 0464e93..a24621b 100644 --- a/libs/binder/Parcel.cpp +++ b/libs/binder/Parcel.cpp @@ -25,6 +25,8 @@ #include <binder/ProcessState.h> #include <binder/TextOutput.h> +#include <errno.h> +#include <utils/CallStack.h> #include <utils/Debug.h> #include <utils/Log.h> #include <utils/String8.h> @@ -35,6 +37,7 @@ #include <private/binder/binder_module.h> +#include <fcntl.h> #include <inttypes.h> #include <stdio.h> #include <stdlib.h> @@ -78,12 +81,12 @@ void acquire_object(const sp<ProcessState>& proc, case BINDER_TYPE_BINDER: if (obj.binder) { LOG_REFS("Parcel %p acquiring reference on local %p", who, obj.cookie); - static_cast<IBinder*>(obj.cookie)->incStrong(who); + reinterpret_cast<IBinder*>(obj.cookie)->incStrong(who); } return; case BINDER_TYPE_WEAK_BINDER: if (obj.binder) - static_cast<RefBase::weakref_type*>(obj.binder)->incWeak(who); + reinterpret_cast<RefBase::weakref_type*>(obj.binder)->incWeak(who); return; case BINDER_TYPE_HANDLE: { const sp<IBinder> b = proc->getStrongProxyForHandle(obj.handle); @@ -105,7 +108,7 @@ void acquire_object(const sp<ProcessState>& proc, } } - ALOGD("Invalid object type 0x%08lx", obj.type); + ALOGD("Invalid object type 0x%08x", obj.type); } void release_object(const sp<ProcessState>& proc, @@ -115,12 +118,12 @@ void release_object(const sp<ProcessState>& proc, case BINDER_TYPE_BINDER: if (obj.binder) { LOG_REFS("Parcel %p releasing reference on local %p", who, obj.cookie); - static_cast<IBinder*>(obj.cookie)->decStrong(who); + reinterpret_cast<IBinder*>(obj.cookie)->decStrong(who); } return; case BINDER_TYPE_WEAK_BINDER: if (obj.binder) - static_cast<RefBase::weakref_type*>(obj.binder)->decWeak(who); + reinterpret_cast<RefBase::weakref_type*>(obj.binder)->decWeak(who); return; case BINDER_TYPE_HANDLE: { const sp<IBinder> b = proc->getStrongProxyForHandle(obj.handle); @@ -136,25 +139,25 @@ void release_object(const sp<ProcessState>& proc, return; } case BINDER_TYPE_FD: { - if (obj.cookie != (void*)0) close(obj.handle); + if (obj.cookie != 0) close(obj.handle); return; } } - ALOGE("Invalid object type 0x%08lx", obj.type); + ALOGE("Invalid object type 0x%08x", obj.type); } inline static status_t finish_flatten_binder( - const sp<IBinder>& binder, const flat_binder_object& flat, Parcel* out) + const sp<IBinder>& /*binder*/, const flat_binder_object& flat, Parcel* out) { return out->writeObject(flat, false); } -status_t flatten_binder(const sp<ProcessState>& proc, +status_t flatten_binder(const sp<ProcessState>& /*proc*/, const sp<IBinder>& binder, Parcel* out) { flat_binder_object obj; - + obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS; if (binder != NULL) { IBinder *local = binder->localBinder(); @@ -165,27 +168,28 @@ status_t flatten_binder(const sp<ProcessState>& proc, } const int32_t handle = proxy ? proxy->handle() : 0; obj.type = BINDER_TYPE_HANDLE; + obj.binder = 0; /* Don't pass uninitialized stack data to a remote process */ obj.handle = handle; - obj.cookie = NULL; + obj.cookie = 0; } else { obj.type = BINDER_TYPE_BINDER; - obj.binder = local->getWeakRefs(); - obj.cookie = local; + obj.binder = reinterpret_cast<uintptr_t>(local->getWeakRefs()); + obj.cookie = reinterpret_cast<uintptr_t>(local); } } else { obj.type = BINDER_TYPE_BINDER; - obj.binder = NULL; - obj.cookie = NULL; + obj.binder = 0; + obj.cookie = 0; } - + return finish_flatten_binder(binder, obj, out); } -status_t flatten_binder(const sp<ProcessState>& proc, +status_t flatten_binder(const sp<ProcessState>& /*proc*/, const wp<IBinder>& binder, Parcel* out) { flat_binder_object obj; - + obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS; if (binder != NULL) { sp<IBinder> real = binder.promote(); @@ -198,16 +202,17 @@ status_t flatten_binder(const sp<ProcessState>& proc, } const int32_t handle = proxy ? proxy->handle() : 0; obj.type = BINDER_TYPE_WEAK_HANDLE; + obj.binder = 0; /* Don't pass uninitialized stack data to a remote process */ obj.handle = handle; - obj.cookie = NULL; + obj.cookie = 0; } else { obj.type = BINDER_TYPE_WEAK_BINDER; - obj.binder = binder.get_refs(); - obj.cookie = binder.unsafe_get(); + obj.binder = reinterpret_cast<uintptr_t>(binder.get_refs()); + obj.cookie = reinterpret_cast<uintptr_t>(binder.unsafe_get()); } return finish_flatten_binder(real, obj, out); } - + // XXX How to deal? In order to flatten the given binder, // we need to probe it for information, which requires a primary // reference... but we don't have one. @@ -217,39 +222,40 @@ status_t flatten_binder(const sp<ProcessState>& proc, // implementation we are using. ALOGE("Unable to unflatten Binder weak reference!"); obj.type = BINDER_TYPE_BINDER; - obj.binder = NULL; - obj.cookie = NULL; + obj.binder = 0; + obj.cookie = 0; return finish_flatten_binder(NULL, obj, out); - + } else { obj.type = BINDER_TYPE_BINDER; - obj.binder = NULL; - obj.cookie = NULL; + obj.binder = 0; + obj.cookie = 0; return finish_flatten_binder(NULL, obj, out); } } inline static status_t finish_unflatten_binder( - BpBinder* proxy, const flat_binder_object& flat, const Parcel& in) + BpBinder* /*proxy*/, const flat_binder_object& /*flat*/, + const Parcel& /*in*/) { return NO_ERROR; } - + status_t unflatten_binder(const sp<ProcessState>& proc, const Parcel& in, sp<IBinder>* out) { const flat_binder_object* flat = in.readObject(false); - + if (flat) { switch (flat->type) { case BINDER_TYPE_BINDER: - *out = static_cast<IBinder*>(flat->cookie); + *out = reinterpret_cast<IBinder*>(flat->cookie); return finish_unflatten_binder(NULL, *flat, in); case BINDER_TYPE_HANDLE: *out = proc->getStrongProxyForHandle(flat->handle); return finish_unflatten_binder( static_cast<BpBinder*>(out->get()), *flat, in); - } + } } return BAD_TYPE; } @@ -258,17 +264,17 @@ status_t unflatten_binder(const sp<ProcessState>& proc, const Parcel& in, wp<IBinder>* out) { const flat_binder_object* flat = in.readObject(false); - + if (flat) { switch (flat->type) { case BINDER_TYPE_BINDER: - *out = static_cast<IBinder*>(flat->cookie); + *out = reinterpret_cast<IBinder*>(flat->cookie); return finish_unflatten_binder(NULL, *flat, in); case BINDER_TYPE_WEAK_BINDER: - if (flat->binder != NULL) { + if (flat->binder != 0) { out->set_object_and_refs( - static_cast<IBinder*>(flat->cookie), - static_cast<RefBase::weakref_type*>(flat->binder)); + reinterpret_cast<IBinder*>(flat->cookie), + reinterpret_cast<RefBase::weakref_type*>(flat->binder)); } else { *out = NULL; } @@ -332,7 +338,7 @@ status_t Parcel::setDataSize(size_t size) err = continueWrite(size); if (err == NO_ERROR) { mDataSize = size; - ALOGV("setDataSize Setting data size of %p to %d\n", this, mDataSize); + ALOGV("setDataSize Setting data size of %p to %zu", this, mDataSize); } return err; } @@ -365,7 +371,7 @@ status_t Parcel::appendFrom(const Parcel *parcel, size_t offset, size_t len) const sp<ProcessState> proc(ProcessState::self()); status_t err; const uint8_t *data = parcel->mData; - const size_t *objects = parcel->mObjects; + const binder_size_t *objects = parcel->mObjects; size_t size = parcel->mObjectsSize; int startPos = mDataPos; int firstIndex = -1, lastIndex = -2; @@ -412,15 +418,15 @@ status_t Parcel::appendFrom(const Parcel *parcel, size_t offset, size_t len) // grow objects if (mObjectsCapacity < mObjectsSize + numObjects) { int newSize = ((mObjectsSize + numObjects)*3)/2; - size_t *objects = - (size_t*)realloc(mObjects, newSize*sizeof(size_t)); - if (objects == (size_t*)0) { + binder_size_t *objects = + (binder_size_t*)realloc(mObjects, newSize*sizeof(binder_size_t)); + if (objects == (binder_size_t*)0) { return NO_MEMORY; } mObjects = objects; mObjectsCapacity = newSize; } - + // append and acquire objects int idx = mObjectsSize; for (int i = firstIndex; i <= lastIndex; i++) { @@ -437,7 +443,7 @@ status_t Parcel::appendFrom(const Parcel *parcel, size_t offset, size_t len) // new Parcel now owns its own fd, and can declare that we // officially know we have fds. flat->handle = dup(flat->handle); - flat->cookie = (void*)1; + flat->cookie = 1; mHasFds = mFdsKnown = true; if (!mAllowFds) { err = FDS_NOT_ALLOWED; @@ -506,13 +512,13 @@ bool Parcel::enforceInterface(const String16& interface, if (str == interface) { return true; } else { - ALOGW("**** enforceInterface() expected '%s' but read '%s'\n", + ALOGW("**** enforceInterface() expected '%s' but read '%s'", String8(interface).string(), String8(str).string()); return false; } } -const size_t* Parcel::objects() const +const binder_size_t* Parcel::objects() const { return mObjects; } @@ -536,10 +542,10 @@ status_t Parcel::finishWrite(size_t len) { //printf("Finish write of %d\n", len); mDataPos += len; - ALOGV("finishWrite Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("finishWrite Setting data pos of %p to %zu", this, mDataPos); if (mDataPos > mDataSize) { mDataSize = mDataPos; - ALOGV("finishWrite Setting data size of %p to %d\n", this, mDataSize); + ALOGV("finishWrite Setting data size of %p to %zu", this, mDataSize); } //printf("New pos=%d, size=%d\n", mDataPos, mDataSize); return NO_ERROR; @@ -644,6 +650,11 @@ status_t Parcel::writeInt64(int64_t val) return writeAligned(val); } +status_t Parcel::writePointer(uintptr_t val) +{ + return writeAligned<binder_uintptr_t>(val); +} + status_t Parcel::writeFloat(float val) { return writeAligned(val); @@ -670,11 +681,6 @@ status_t Parcel::writeDouble(double val) #endif -status_t Parcel::writeIntPtr(intptr_t val) -{ - return writeAligned(val); -} - status_t Parcel::writeCString(const char* str) { return write(str, strlen(str)+1); @@ -700,7 +706,7 @@ status_t Parcel::writeString16(const String16& str) status_t Parcel::writeString16(const char16_t* str, size_t len) { if (str == NULL) return writeInt32(-1); - + status_t err = writeInt32(len); if (err == NO_ERROR) { len *= sizeof(char16_t); @@ -753,14 +759,38 @@ status_t Parcel::writeFileDescriptor(int fd, bool takeOwnership) flat_binder_object obj; obj.type = BINDER_TYPE_FD; obj.flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS; + obj.binder = 0; /* Don't pass uninitialized stack data to a remote process */ obj.handle = fd; - obj.cookie = (void*) (takeOwnership ? 1 : 0); + obj.cookie = takeOwnership ? 1 : 0; return writeObject(obj, true); } status_t Parcel::writeDupFileDescriptor(int fd) { int dupFd = dup(fd); + + { // Temporary extra debug validation for b/17477219: a Parcel recipient is + // getting a positive but invalid fd unexpectedly. Trying to track down + // where it's coming from. + int dupErrno = dupFd < 0 ? errno : 0; + int fdFlags = fcntl(fd, F_GETFD); + int fdFlagsErrno = fdFlags == -1 ? errno : 0; + int dupFlags = fcntl(dupFd, F_GETFD); + int dupFlagsErrno = dupFlags == -1 ? errno : 0; + if (dupFd < 0 || fdFlags == -1 || dupFlags == -1) { + ALOGE("Parcel::writeDupFileDescriptor failed:\n" + " fd=%d flags=%d err=%d(%s)\n" + " dupFd=%d dupErr=%d(%s) flags=%d err=%d(%s)", + fd, fdFlags, fdFlagsErrno, strerror(fdFlagsErrno), + dupFd, dupErrno, strerror(dupErrno), + dupFlags, dupFlagsErrno, strerror(dupFlagsErrno)); + if (fd < 0 || fdFlags == -1) { + CallStack(LOG_TAG); + } + return -errno; + } + } + if (dupFd < 0) { return -errno; } @@ -771,6 +801,32 @@ status_t Parcel::writeDupFileDescriptor(int fd) return err; } +// WARNING: This method must stay in sync with +// Parcelable.Creator<ParcelFileDescriptor> CREATOR +// in frameworks/base/core/java/android/os/ParcelFileDescriptor.java +status_t Parcel::writeParcelFileDescriptor(int fd, int commChannel) { + status_t status; + + if (fd < 0) { + status = writeInt32(0); // ParcelFileDescriptor is null + if (status) return status; + } else { + status = writeInt32(1); // ParcelFileDescriptor is not null + if (status) return status; + status = writeDupFileDescriptor(fd); + if (status) return status; + if (commChannel < 0) { + status = writeInt32(0); // commChannel is null + if (status) return status; + } else { + status = writeInt32(1); // commChannel is not null + if (status) return status; + status = writeDupFileDescriptor(commChannel); + } + } + return status; +} + status_t Parcel::writeBlob(size_t len, WritableBlob* outBlob) { status_t status; @@ -862,14 +918,14 @@ status_t Parcel::writeObject(const flat_binder_object& val, bool nullMetaData) if (enoughData && enoughObjects) { restart_write: *reinterpret_cast<flat_binder_object*>(mData+mDataPos) = val; - + // Need to write meta-data? - if (nullMetaData || val.binder != NULL) { + if (nullMetaData || val.binder != 0) { mObjects[mObjectsSize] = mDataPos; acquire_object(ProcessState::self(), val, this); mObjectsSize++; } - + // remember if it's a file descriptor if (val.type == BINDER_TYPE_FD) { if (!mAllowFds) { @@ -887,12 +943,12 @@ restart_write: } if (!enoughObjects) { size_t newSize = ((mObjectsSize+2)*3)/2; - size_t* objects = (size_t*)realloc(mObjects, newSize*sizeof(size_t)); + binder_size_t* objects = (binder_size_t*)realloc(mObjects, newSize*sizeof(binder_size_t)); if (objects == NULL) return NO_MEMORY; mObjects = objects; mObjectsCapacity = newSize; } - + goto restart_write; } @@ -901,7 +957,7 @@ status_t Parcel::writeNoException() return writeInt32(0); } -void Parcel::remove(size_t start, size_t amt) +void Parcel::remove(size_t /*start*/, size_t /*amt*/) { LOG_ALWAYS_FATAL("Parcel::remove() not yet implemented!"); } @@ -912,7 +968,7 @@ status_t Parcel::read(void* outData, size_t len) const && len <= PAD_SIZE(len)) { memcpy(outData, mData+mDataPos, len); mDataPos += PAD_SIZE(len); - ALOGV("read Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("read Setting data pos of %p to %zu", this, mDataPos); return NO_ERROR; } return NOT_ENOUGH_DATA; @@ -924,7 +980,7 @@ const void* Parcel::readInplace(size_t len) const && len <= PAD_SIZE(len)) { const void* data = mData+mDataPos; mDataPos += PAD_SIZE(len); - ALOGV("readInplace Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("readInplace Setting data pos of %p to %zu", this, mDataPos); return data; } return NULL; @@ -991,6 +1047,22 @@ int64_t Parcel::readInt64() const return readAligned<int64_t>(); } +status_t Parcel::readPointer(uintptr_t *pArg) const +{ + status_t ret; + binder_uintptr_t ptr; + ret = readAligned(&ptr); + if (!ret) + *pArg = ptr; + return ret; +} + +uintptr_t Parcel::readPointer() const +{ + return readAligned<binder_uintptr_t>(); +} + + status_t Parcel::readFloat(float *pArg) const { return readAligned(pArg); @@ -1010,6 +1082,7 @@ status_t Parcel::readDouble(double *pArg) const double d; unsigned long long ll; } u; + u.d = 0; status_t status; status = readAligned(&u.ll); *pArg = u.d; @@ -1062,7 +1135,7 @@ const char* Parcel::readCString() const if (eos) { const size_t len = eos - str; mDataPos += PAD_SIZE(len+1); - ALOGV("readCString Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("readCString Setting data pos of %p to %zu", this, mDataPos); return str; } } @@ -1168,13 +1241,30 @@ int Parcel::readFileDescriptor() const if (flat) { switch (flat->type) { case BINDER_TYPE_FD: - //ALOGI("Returning file descriptor %ld from parcel %p\n", flat->handle, this); + //ALOGI("Returning file descriptor %ld from parcel %p", flat->handle, this); return flat->handle; - } + } } return BAD_TYPE; } +// WARNING: This method must stay in sync with writeToParcel() +// in frameworks/base/core/java/android/os/ParcelFileDescriptor.java +int Parcel::readParcelFileDescriptor(int& outCommChannel) const { + int fd; + outCommChannel = -1; + + if (readInt32() == 0) { + fd = -1; + } else { + fd = readFileDescriptor(); + if (fd >= 0 && readInt32() != 0) { + outCommChannel = readFileDescriptor(); + } + } + return fd; +} + status_t Parcel::readBlob(size_t len, ReadableBlob* outBlob) const { int32_t useAshmem; @@ -1195,7 +1285,7 @@ status_t Parcel::readBlob(size_t len, ReadableBlob* outBlob) const if (fd == int(BAD_TYPE)) return BAD_VALUE; void* ptr = ::mmap(NULL, len, PROT_READ, MAP_SHARED, fd, 0); - if (!ptr) return NO_MEMORY; + if (ptr == MAP_FAILED) return NO_MEMORY; outBlob->init(true /*mapped*/, ptr, len); return NO_ERROR; @@ -1219,8 +1309,24 @@ status_t Parcel::read(FlattenableHelperInterface& val) const status_t err = NO_ERROR; for (size_t i=0 ; i<fd_count && err==NO_ERROR ; i++) { - fds[i] = dup(this->readFileDescriptor()); - if (fds[i] < 0) err = BAD_VALUE; + int oldfd = this->readFileDescriptor(); + fds[i] = dup(oldfd); + if (fds[i] < 0) { + int dupErrno = errno; + err = BAD_VALUE; + int flags = fcntl(oldfd, F_GETFD); + int fcntlErrno = errno; + const flat_binder_object* flat = readObject(true); + ALOGE("dup failed in Parcel::read, fd %zu of %zu\n" + " dup(%d) = %d [errno: %d (%s)]\n" + " fcntl(%d, F_GETFD) = %d [errno: %d (%s)]\n" + " flat %p type %d", + i, fd_count, + oldfd, fds[i], dupErrno, strerror(dupErrno), + oldfd, flags, fcntlErrno, strerror(fcntlErrno), + flat, flat ? flat->type : 0); + CallStack(LOG_TAG); + } } if (err == NO_ERROR) { @@ -1240,23 +1346,23 @@ const flat_binder_object* Parcel::readObject(bool nullMetaData) const const flat_binder_object* obj = reinterpret_cast<const flat_binder_object*>(mData+DPOS); mDataPos = DPOS + sizeof(flat_binder_object); - if (!nullMetaData && (obj->cookie == NULL && obj->binder == NULL)) { + if (!nullMetaData && (obj->cookie == 0 && obj->binder == 0)) { // When transferring a NULL object, we don't write it into // the object list, so we don't want to check for it when // reading. - ALOGV("readObject Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("readObject Setting data pos of %p to %zu", this, mDataPos); return obj; } - + // Ensure that this object is valid... - size_t* const OBJS = mObjects; + binder_size_t* const OBJS = mObjects; const size_t N = mObjectsSize; size_t opos = mNextObjectHint; - + if (N > 0) { - ALOGV("Parcel %p looking for obj at %d, hint=%d\n", + ALOGV("Parcel %p looking for obj at %zu, hint=%zu", this, DPOS, opos); - + // Start at the current hint position, looking for an object at // the current data position. if (opos < N) { @@ -1268,27 +1374,27 @@ const flat_binder_object* Parcel::readObject(bool nullMetaData) const } if (OBJS[opos] == DPOS) { // Found it! - ALOGV("Parcel found obj %d at index %d with forward search", + ALOGV("Parcel %p found obj %zu at index %zu with forward search", this, DPOS, opos); mNextObjectHint = opos+1; - ALOGV("readObject Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("readObject Setting data pos of %p to %zu", this, mDataPos); return obj; } - + // Look backwards for it... while (opos > 0 && OBJS[opos] > DPOS) { opos--; } if (OBJS[opos] == DPOS) { // Found it! - ALOGV("Parcel found obj %d at index %d with backward search", + ALOGV("Parcel %p found obj %zu at index %zu with backward search", this, DPOS, opos); mNextObjectHint = opos+1; - ALOGV("readObject Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("readObject Setting data pos of %p to %zu", this, mDataPos); return obj; } } - ALOGW("Attempt to read object from Parcel %p at offset %d that is not in the object list", + ALOGW("Attempt to read object from Parcel %p at offset %zu that is not in the object list", this, DPOS); } return NULL; @@ -1298,22 +1404,22 @@ void Parcel::closeFileDescriptors() { size_t i = mObjectsSize; if (i > 0) { - //ALOGI("Closing file descriptors for %d objects...", mObjectsSize); + //ALOGI("Closing file descriptors for %zu objects...", i); } while (i > 0) { i--; const flat_binder_object* flat = reinterpret_cast<flat_binder_object*>(mData+mObjects[i]); if (flat->type == BINDER_TYPE_FD) { - //ALOGI("Closing fd: %ld\n", flat->handle); + //ALOGI("Closing fd: %ld", flat->handle); close(flat->handle); } } } -const uint8_t* Parcel::ipcData() const +uintptr_t Parcel::ipcData() const { - return mData; + return reinterpret_cast<uintptr_t>(mData); } size_t Parcel::ipcDataSize() const @@ -1321,9 +1427,9 @@ size_t Parcel::ipcDataSize() const return (mDataSize > mDataPos ? mDataSize : mDataPos); } -const size_t* Parcel::ipcObjects() const +uintptr_t Parcel::ipcObjects() const { - return mObjects; + return reinterpret_cast<uintptr_t>(mObjects); } size_t Parcel::ipcObjectsCount() const @@ -1332,26 +1438,26 @@ size_t Parcel::ipcObjectsCount() const } void Parcel::ipcSetDataReference(const uint8_t* data, size_t dataSize, - const size_t* objects, size_t objectsCount, release_func relFunc, void* relCookie) + const binder_size_t* objects, size_t objectsCount, release_func relFunc, void* relCookie) { - size_t minOffset = 0; + binder_size_t minOffset = 0; freeDataNoInit(); mError = NO_ERROR; mData = const_cast<uint8_t*>(data); mDataSize = mDataCapacity = dataSize; - //ALOGI("setDataReference Setting data size of %p to %lu (pid=%d)\n", this, mDataSize, getpid()); + //ALOGI("setDataReference Setting data size of %p to %lu (pid=%d)", this, mDataSize, getpid()); mDataPos = 0; - ALOGV("setDataReference Setting data pos of %p to %d\n", this, mDataPos); - mObjects = const_cast<size_t*>(objects); + ALOGV("setDataReference Setting data pos of %p to %zu", this, mDataPos); + mObjects = const_cast<binder_size_t*>(objects); mObjectsSize = mObjectsCapacity = objectsCount; mNextObjectHint = 0; mOwner = relFunc; mOwnerCookie = relCookie; for (size_t i = 0; i < mObjectsSize; i++) { - size_t offset = mObjects[i]; + binder_size_t offset = mObjects[i]; if (offset < minOffset) { - ALOGE("%s: bad object offset %zu < %zu\n", - __func__, offset, minOffset); + ALOGE("%s: bad object offset %"PRIu64" < %"PRIu64"\n", + __func__, (uint64_t)offset, (uint64_t)minOffset); mObjectsSize = 0; break; } @@ -1360,17 +1466,17 @@ void Parcel::ipcSetDataReference(const uint8_t* data, size_t dataSize, scanForFds(); } -void Parcel::print(TextOutput& to, uint32_t flags) const +void Parcel::print(TextOutput& to, uint32_t /*flags*/) const { to << "Parcel("; - + if (errorCheck() != NO_ERROR) { const status_t err = errorCheck(); - to << "Error: " << (void*)err << " \"" << strerror(-err) << "\""; + to << "Error: " << (void*)(intptr_t)err << " \"" << strerror(-err) << "\""; } else if (dataSize() > 0) { const uint8_t* DATA = data(); to << indent << HexDump(DATA, dataSize()) << dedent; - const size_t* OBJS = objects(); + const binder_size_t* OBJS = objects(); const size_t N = objectsCount(); for (size_t i=0; i<N; i++) { const flat_binder_object* flat @@ -1382,7 +1488,7 @@ void Parcel::print(TextOutput& to, uint32_t flags) const } else { to << "NULL"; } - + to << ")"; } @@ -1391,7 +1497,7 @@ void Parcel::releaseObjects() const sp<ProcessState> proc(ProcessState::self()); size_t i = mObjectsSize; uint8_t* const data = mData; - size_t* const objects = mObjects; + binder_size_t* const objects = mObjects; while (i > 0) { i--; const flat_binder_object* flat @@ -1405,7 +1511,7 @@ void Parcel::acquireObjects() const sp<ProcessState> proc(ProcessState::self()); size_t i = mObjectsSize; uint8_t* const data = mData; - size_t* const objects = mObjects; + binder_size_t* const objects = mObjects; while (i > 0) { i--; const flat_binder_object* flat @@ -1423,7 +1529,7 @@ void Parcel::freeData() void Parcel::freeDataNoInit() { if (mOwner) { - //ALOGI("Freeing data ref of %p (pid=%d)\n", this, getpid()); + //ALOGI("Freeing data ref of %p (pid=%d)", this, getpid()); mOwner(this, mData, mDataSize, mObjects, mObjectsSize, mOwnerCookie); } else { releaseObjects(); @@ -1446,24 +1552,24 @@ status_t Parcel::restartWrite(size_t desired) freeData(); return continueWrite(desired); } - + uint8_t* data = (uint8_t*)realloc(mData, desired); if (!data && desired > mDataCapacity) { mError = NO_MEMORY; return NO_MEMORY; } - + releaseObjects(); - + if (data) { mData = data; mDataCapacity = desired; } - + mDataSize = mDataPos = 0; - ALOGV("restartWrite Setting data size of %p to %d\n", this, mDataSize); - ALOGV("restartWrite Setting data pos of %p to %d\n", this, mDataPos); - + ALOGV("restartWrite Setting data size of %p to %zu", this, mDataSize); + ALOGV("restartWrite Setting data pos of %p to %zu", this, mDataPos); + free(mObjects); mObjects = NULL; mObjectsSize = mObjectsCapacity = 0; @@ -1471,7 +1577,7 @@ status_t Parcel::restartWrite(size_t desired) mHasFds = false; mFdsKnown = true; mAllowFds = true; - + return NO_ERROR; } @@ -1491,7 +1597,7 @@ status_t Parcel::continueWrite(size_t desired) } } } - + if (mOwner) { // If the size is going to zero, just release the owner's data. if (desired == 0) { @@ -1506,10 +1612,10 @@ status_t Parcel::continueWrite(size_t desired) mError = NO_MEMORY; return NO_MEMORY; } - size_t* objects = NULL; - + binder_size_t* objects = NULL; + if (objectsSize) { - objects = (size_t*)malloc(objectsSize*sizeof(size_t)); + objects = (binder_size_t*)malloc(objectsSize*sizeof(binder_size_t)); if (!objects) { free(data); @@ -1524,21 +1630,21 @@ status_t Parcel::continueWrite(size_t desired) acquireObjects(); mObjectsSize = oldObjectsSize; } - + if (mData) { memcpy(data, mData, mDataSize < desired ? mDataSize : desired); } if (objects && mObjects) { - memcpy(objects, mObjects, objectsSize*sizeof(size_t)); + memcpy(objects, mObjects, objectsSize*sizeof(binder_size_t)); } - //ALOGI("Freeing data ref of %p (pid=%d)\n", this, getpid()); + //ALOGI("Freeing data ref of %p (pid=%d)", this, getpid()); mOwner(this, mData, mDataSize, mObjects, mObjectsSize, mOwnerCookie); mOwner = NULL; mData = data; mObjects = objects; mDataSize = (mDataSize < desired) ? mDataSize : desired; - ALOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize); + ALOGV("continueWrite Setting data size of %p to %zu", this, mDataSize); mDataCapacity = desired; mObjectsSize = mObjectsCapacity = objectsSize; mNextObjectHint = 0; @@ -1556,8 +1662,8 @@ status_t Parcel::continueWrite(size_t desired) } release_object(proc, *flat, this); } - size_t* objects = - (size_t*)realloc(mObjects, objectsSize*sizeof(size_t)); + binder_size_t* objects = + (binder_size_t*)realloc(mObjects, objectsSize*sizeof(binder_size_t)); if (objects) { mObjects = objects; } @@ -1578,14 +1684,14 @@ status_t Parcel::continueWrite(size_t desired) } else { if (mDataSize > desired) { mDataSize = desired; - ALOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize); + ALOGV("continueWrite Setting data size of %p to %zu", this, mDataSize); } if (mDataPos > desired) { mDataPos = desired; - ALOGV("continueWrite Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("continueWrite Setting data pos of %p to %zu", this, mDataPos); } } - + } else { // This is the first data. Easy! uint8_t* data = (uint8_t*)malloc(desired); @@ -1596,13 +1702,13 @@ status_t Parcel::continueWrite(size_t desired) if(!(mDataCapacity == 0 && mObjects == NULL && mObjectsCapacity == 0)) { - ALOGE("continueWrite: %d/%p/%d/%d", mDataCapacity, mObjects, mObjectsCapacity, desired); + ALOGE("continueWrite: %zu/%p/%zu/%zu", mDataCapacity, mObjects, mObjectsCapacity, desired); } - + mData = data; mDataSize = mDataPos = 0; - ALOGV("continueWrite Setting data size of %p to %d\n", this, mDataSize); - ALOGV("continueWrite Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("continueWrite Setting data size of %p to %zu", this, mDataSize); + ALOGV("continueWrite Setting data pos of %p to %zu", this, mDataPos); mDataCapacity = desired; } @@ -1616,8 +1722,8 @@ void Parcel::initState() mDataSize = 0; mDataCapacity = 0; mDataPos = 0; - ALOGV("initState Setting data size of %p to %d\n", this, mDataSize); - ALOGV("initState Setting data pos of %p to %d\n", this, mDataPos); + ALOGV("initState Setting data size of %p to %zu", this, mDataSize); + ALOGV("initState Setting data pos of %p to %zu", this, mDataPos); mObjects = NULL; mObjectsSize = 0; mObjectsCapacity = 0; diff --git a/libs/binder/ProcessState.cpp b/libs/binder/ProcessState.cpp index c1e49bc..303d6cf 100644 --- a/libs/binder/ProcessState.cpp +++ b/libs/binder/ProcessState.cpp @@ -48,11 +48,6 @@ namespace android { -// Global variables -int mArgC; -const char* const* mArgV; -int mArgLen; - class PoolThread : public Thread { public: @@ -86,7 +81,7 @@ void ProcessState::setContextObject(const sp<IBinder>& object) setContextObject(object, String16("default")); } -sp<IBinder> ProcessState::getContextObject(const sp<IBinder>& caller) +sp<IBinder> ProcessState::getContextObject(const sp<IBinder>& /*caller*/) { return getStrongProxyForHandle(0); } @@ -280,36 +275,6 @@ void ProcessState::expungeHandle(int32_t handle, IBinder* binder) if (e && e->binder == binder) e->binder = NULL; } -void ProcessState::setArgs(int argc, const char* const argv[]) -{ - mArgC = argc; - mArgV = (const char **)argv; - - mArgLen = 0; - for (int i=0; i<argc; i++) { - mArgLen += strlen(argv[i]) + 1; - } - mArgLen--; -} - -int ProcessState::getArgC() const -{ - return mArgC; -} - -const char* const* ProcessState::getArgV() const -{ - return mArgV; -} - -void ProcessState::setArgV0(const char* txt) -{ - if (mArgV != NULL) { - strncpy((char*)mArgV[0], txt, mArgLen); - set_process_name(txt); - } -} - String8 ProcessState::makeBinderThreadName() { int32_t s = android_atomic_add(1, &mThreadPoolSeq); String8 name; @@ -345,7 +310,7 @@ static int open_driver() int fd = open("/dev/binder", O_RDWR); if (fd >= 0) { fcntl(fd, F_SETFD, FD_CLOEXEC); - int vers; + int vers = 0; status_t result = ioctl(fd, BINDER_VERSION, &vers); if (result == -1) { ALOGE("Binder ioctl to obtain version failed: %s", strerror(errno)); |