Home | History | Annotate | Download | only in binder
      1 /*
      2  * Copyright (C) 2005 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #include <binder/Binder.h>
     18 
     19 #include <stdatomic.h>
     20 #include <utils/misc.h>
     21 #include <binder/BpBinder.h>
     22 #include <binder/IInterface.h>
     23 #include <binder/Parcel.h>
     24 
     25 #include <stdio.h>
     26 
     27 namespace android {
     28 
     29 // ---------------------------------------------------------------------------
     30 
     31 IBinder::IBinder()
     32     : RefBase()
     33 {
     34 }
     35 
     36 IBinder::~IBinder()
     37 {
     38 }
     39 
     40 // ---------------------------------------------------------------------------
     41 
     42 sp<IInterface>  IBinder::queryLocalInterface(const String16& /*descriptor*/)
     43 {
     44     return NULL;
     45 }
     46 
     47 BBinder* IBinder::localBinder()
     48 {
     49     return NULL;
     50 }
     51 
     52 BpBinder* IBinder::remoteBinder()
     53 {
     54     return NULL;
     55 }
     56 
     57 bool IBinder::checkSubclass(const void* /*subclassID*/) const
     58 {
     59     return false;
     60 }
     61 
     62 // ---------------------------------------------------------------------------
     63 
     64 class BBinder::Extras
     65 {
     66 public:
     67     Mutex mLock;
     68     BpBinder::ObjectManager mObjects;
     69 };
     70 
     71 // ---------------------------------------------------------------------------
     72 
     73 BBinder::BBinder()
     74 {
     75   atomic_init(&mExtras, static_cast<uintptr_t>(0));
     76 }
     77 
     78 bool BBinder::isBinderAlive() const
     79 {
     80     return true;
     81 }
     82 
     83 status_t BBinder::pingBinder()
     84 {
     85     return NO_ERROR;
     86 }
     87 
     88 const String16& BBinder::getInterfaceDescriptor() const
     89 {
     90     // This is a local static rather than a global static,
     91     // to avoid static initializer ordering issues.
     92     static String16 sEmptyDescriptor;
     93     ALOGW("reached BBinder::getInterfaceDescriptor (this=%p)", this);
     94     return sEmptyDescriptor;
     95 }
     96 
     97 status_t BBinder::transact(
     98     uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
     99 {
    100     data.setDataPosition(0);
    101 
    102     status_t err = NO_ERROR;
    103     switch (code) {
    104         case PING_TRANSACTION:
    105             reply->writeInt32(pingBinder());
    106             break;
    107         default:
    108             err = onTransact(code, data, reply, flags);
    109             break;
    110     }
    111 
    112     if (reply != NULL) {
    113         reply->setDataPosition(0);
    114     }
    115 
    116     return err;
    117 }
    118 
    119 status_t BBinder::linkToDeath(
    120     const sp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
    121     uint32_t /*flags*/)
    122 {
    123     return INVALID_OPERATION;
    124 }
    125 
    126 status_t BBinder::unlinkToDeath(
    127     const wp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
    128     uint32_t /*flags*/, wp<DeathRecipient>* /*outRecipient*/)
    129 {
    130     return INVALID_OPERATION;
    131 }
    132 
    133     status_t BBinder::dump(int /*fd*/, const Vector<String16>& /*args*/)
    134 {
    135     return NO_ERROR;
    136 }
    137 
    138 void BBinder::attachObject(
    139     const void* objectID, void* object, void* cleanupCookie,
    140     object_cleanup_func func)
    141 {
    142     Extras* e = reinterpret_cast<Extras*>(
    143                     atomic_load_explicit(&mExtras, memory_order_acquire));
    144 
    145     if (!e) {
    146         e = new Extras;
    147         uintptr_t expected = 0;
    148         if (!atomic_compare_exchange_strong_explicit(
    149                                         &mExtras, &expected,
    150                                         reinterpret_cast<uintptr_t>(e),
    151                                         memory_order_release,
    152                                         memory_order_acquire)) {
    153             delete e;
    154             e = reinterpret_cast<Extras*>(expected);  // Filled in by CAS
    155         }
    156         if (e == 0) return; // out of memory
    157     }
    158 
    159     AutoMutex _l(e->mLock);
    160     e->mObjects.attach(objectID, object, cleanupCookie, func);
    161 }
    162 
    163 // The C11 standard doesn't allow atomic loads from const fields,
    164 // though C++11 does.  Fudge it until standards get straightened out.
    165 static inline uintptr_t load_const_atomic(const atomic_uintptr_t* p,
    166                                           memory_order mo) {
    167     atomic_uintptr_t* non_const_p = const_cast<atomic_uintptr_t*>(p);
    168     return atomic_load_explicit(non_const_p, mo);
    169 }
    170 
    171 void* BBinder::findObject(const void* objectID) const
    172 {
    173     Extras* e = reinterpret_cast<Extras*>(
    174                     load_const_atomic(&mExtras, memory_order_acquire));
    175     if (!e) return NULL;
    176 
    177     AutoMutex _l(e->mLock);
    178     return e->mObjects.find(objectID);
    179 }
    180 
    181 void BBinder::detachObject(const void* objectID)
    182 {
    183     Extras* e = reinterpret_cast<Extras*>(
    184                     atomic_load_explicit(&mExtras, memory_order_acquire));
    185     if (!e) return;
    186 
    187     AutoMutex _l(e->mLock);
    188     e->mObjects.detach(objectID);
    189 }
    190 
    191 BBinder* BBinder::localBinder()
    192 {
    193     return this;
    194 }
    195 
    196 BBinder::~BBinder()
    197 {
    198     Extras* e = reinterpret_cast<Extras*>(
    199                     atomic_load_explicit(&mExtras, memory_order_relaxed));
    200     if (e) delete e;
    201 }
    202 
    203 
    204 status_t BBinder::onTransact(
    205     uint32_t code, const Parcel& data, Parcel* reply, uint32_t /*flags*/)
    206 {
    207     switch (code) {
    208         case INTERFACE_TRANSACTION:
    209             reply->writeString16(getInterfaceDescriptor());
    210             return NO_ERROR;
    211 
    212         case DUMP_TRANSACTION: {
    213             int fd = data.readFileDescriptor();
    214             int argc = data.readInt32();
    215             Vector<String16> args;
    216             for (int i = 0; i < argc && data.dataAvail() > 0; i++) {
    217                args.add(data.readString16());
    218             }
    219             return dump(fd, args);
    220         }
    221 
    222         case SYSPROPS_TRANSACTION: {
    223             report_sysprop_change();
    224             return NO_ERROR;
    225         }
    226 
    227         default:
    228             return UNKNOWN_TRANSACTION;
    229     }
    230 }
    231 
    232 // ---------------------------------------------------------------------------
    233 
    234 enum {
    235     // This is used to transfer ownership of the remote binder from
    236     // the BpRefBase object holding it (when it is constructed), to the
    237     // owner of the BpRefBase object when it first acquires that BpRefBase.
    238     kRemoteAcquired = 0x00000001
    239 };
    240 
    241 BpRefBase::BpRefBase(const sp<IBinder>& o)
    242     : mRemote(o.get()), mRefs(NULL), mState(0)
    243 {
    244     extendObjectLifetime(OBJECT_LIFETIME_WEAK);
    245 
    246     if (mRemote) {
    247         mRemote->incStrong(this);           // Removed on first IncStrong().
    248         mRefs = mRemote->createWeak(this);  // Held for our entire lifetime.
    249     }
    250 }
    251 
    252 BpRefBase::~BpRefBase()
    253 {
    254     if (mRemote) {
    255         if (!(mState&kRemoteAcquired)) {
    256             mRemote->decStrong(this);
    257         }
    258         mRefs->decWeak(this);
    259     }
    260 }
    261 
    262 void BpRefBase::onFirstRef()
    263 {
    264     android_atomic_or(kRemoteAcquired, &mState);
    265 }
    266 
    267 void BpRefBase::onLastStrongRef(const void* /*id*/)
    268 {
    269     if (mRemote) {
    270         mRemote->decStrong(this);
    271     }
    272 }
    273 
    274 bool BpRefBase::onIncStrongAttempted(uint32_t /*flags*/, const void* /*id*/)
    275 {
    276     return mRemote ? mRefs->attemptIncStrong(this) : false;
    277 }
    278 
    279 // ---------------------------------------------------------------------------
    280 
    281 }; // namespace android
    282