xref: /aosp_15_r20/system/libhwbinder/Binder.cpp (revision 77b80299c8bdfeca3ae6d0ce27ae1ad3db289be3)
1*77b80299SAndroid Build Coastguard Worker /*
2*77b80299SAndroid Build Coastguard Worker  * Copyright (C) 2005 The Android Open Source Project
3*77b80299SAndroid Build Coastguard Worker  *
4*77b80299SAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*77b80299SAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*77b80299SAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*77b80299SAndroid Build Coastguard Worker  *
8*77b80299SAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*77b80299SAndroid Build Coastguard Worker  *
10*77b80299SAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*77b80299SAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*77b80299SAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*77b80299SAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*77b80299SAndroid Build Coastguard Worker  * limitations under the License.
15*77b80299SAndroid Build Coastguard Worker  */
16*77b80299SAndroid Build Coastguard Worker 
17*77b80299SAndroid Build Coastguard Worker #include <hwbinder/Binder.h>
18*77b80299SAndroid Build Coastguard Worker 
19*77b80299SAndroid Build Coastguard Worker #include <android-base/macros.h>
20*77b80299SAndroid Build Coastguard Worker #include <cutils/android_filesystem_config.h>
21*77b80299SAndroid Build Coastguard Worker #include <cutils/multiuser.h>
22*77b80299SAndroid Build Coastguard Worker #include <hwbinder/BpHwBinder.h>
23*77b80299SAndroid Build Coastguard Worker #include <hwbinder/IInterface.h>
24*77b80299SAndroid Build Coastguard Worker #include <hwbinder/IPCThreadState.h>
25*77b80299SAndroid Build Coastguard Worker #include <hwbinder/Parcel.h>
26*77b80299SAndroid Build Coastguard Worker #include <utils/Log.h>
27*77b80299SAndroid Build Coastguard Worker #include <utils/misc.h>
28*77b80299SAndroid Build Coastguard Worker 
29*77b80299SAndroid Build Coastguard Worker #include <linux/sched.h>
30*77b80299SAndroid Build Coastguard Worker #include <stdio.h>
31*77b80299SAndroid Build Coastguard Worker 
32*77b80299SAndroid Build Coastguard Worker #include <atomic>
33*77b80299SAndroid Build Coastguard Worker 
34*77b80299SAndroid Build Coastguard Worker namespace android {
35*77b80299SAndroid Build Coastguard Worker namespace hardware {
36*77b80299SAndroid Build Coastguard Worker 
37*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
38*77b80299SAndroid Build Coastguard Worker 
IBinder()39*77b80299SAndroid Build Coastguard Worker IBinder::IBinder()
40*77b80299SAndroid Build Coastguard Worker     : RefBase()
41*77b80299SAndroid Build Coastguard Worker {
42*77b80299SAndroid Build Coastguard Worker }
43*77b80299SAndroid Build Coastguard Worker 
~IBinder()44*77b80299SAndroid Build Coastguard Worker IBinder::~IBinder()
45*77b80299SAndroid Build Coastguard Worker {
46*77b80299SAndroid Build Coastguard Worker }
47*77b80299SAndroid Build Coastguard Worker 
48*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
49*77b80299SAndroid Build Coastguard Worker 
localBinder()50*77b80299SAndroid Build Coastguard Worker BHwBinder* IBinder::localBinder()
51*77b80299SAndroid Build Coastguard Worker {
52*77b80299SAndroid Build Coastguard Worker     return nullptr;
53*77b80299SAndroid Build Coastguard Worker }
54*77b80299SAndroid Build Coastguard Worker 
remoteBinder()55*77b80299SAndroid Build Coastguard Worker BpHwBinder* IBinder::remoteBinder()
56*77b80299SAndroid Build Coastguard Worker {
57*77b80299SAndroid Build Coastguard Worker     return nullptr;
58*77b80299SAndroid Build Coastguard Worker }
59*77b80299SAndroid Build Coastguard Worker 
checkSubclass(const void *) const60*77b80299SAndroid Build Coastguard Worker bool IBinder::checkSubclass(const void* /*subclassID*/) const
61*77b80299SAndroid Build Coastguard Worker {
62*77b80299SAndroid Build Coastguard Worker     return false;
63*77b80299SAndroid Build Coastguard Worker }
64*77b80299SAndroid Build Coastguard Worker 
65*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
66*77b80299SAndroid Build Coastguard Worker 
67*77b80299SAndroid Build Coastguard Worker class BHwBinder::Extras
68*77b80299SAndroid Build Coastguard Worker {
69*77b80299SAndroid Build Coastguard Worker public:
70*77b80299SAndroid Build Coastguard Worker     // unlocked objects
71*77b80299SAndroid Build Coastguard Worker     bool mRequestingSid = false;
72*77b80299SAndroid Build Coastguard Worker 
73*77b80299SAndroid Build Coastguard Worker     // for below objects
74*77b80299SAndroid Build Coastguard Worker     Mutex mLock;
75*77b80299SAndroid Build Coastguard Worker     BpHwBinder::ObjectManager mObjects;
76*77b80299SAndroid Build Coastguard Worker };
77*77b80299SAndroid Build Coastguard Worker 
78*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
79*77b80299SAndroid Build Coastguard Worker 
BHwBinder()80*77b80299SAndroid Build Coastguard Worker BHwBinder::BHwBinder() : mSchedPolicy(SCHED_NORMAL), mSchedPriority(0), mExtras(nullptr)
81*77b80299SAndroid Build Coastguard Worker {
82*77b80299SAndroid Build Coastguard Worker }
83*77b80299SAndroid Build Coastguard Worker 
getMinSchedulingPolicy()84*77b80299SAndroid Build Coastguard Worker int BHwBinder::getMinSchedulingPolicy() {
85*77b80299SAndroid Build Coastguard Worker     return mSchedPolicy;
86*77b80299SAndroid Build Coastguard Worker }
87*77b80299SAndroid Build Coastguard Worker 
getMinSchedulingPriority()88*77b80299SAndroid Build Coastguard Worker int BHwBinder::getMinSchedulingPriority() {
89*77b80299SAndroid Build Coastguard Worker     return mSchedPriority;
90*77b80299SAndroid Build Coastguard Worker }
91*77b80299SAndroid Build Coastguard Worker 
isRequestingSid()92*77b80299SAndroid Build Coastguard Worker bool BHwBinder::isRequestingSid() {
93*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_acquire);
94*77b80299SAndroid Build Coastguard Worker 
95*77b80299SAndroid Build Coastguard Worker     return e && e->mRequestingSid;
96*77b80299SAndroid Build Coastguard Worker }
97*77b80299SAndroid Build Coastguard Worker 
setRequestingSid(bool requestingSid)98*77b80299SAndroid Build Coastguard Worker void BHwBinder::setRequestingSid(bool requestingSid) {
99*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_acquire);
100*77b80299SAndroid Build Coastguard Worker 
101*77b80299SAndroid Build Coastguard Worker     if (!e) {
102*77b80299SAndroid Build Coastguard Worker         // default is false. Most things don't need sids, so avoiding allocations when possible.
103*77b80299SAndroid Build Coastguard Worker         if (!requestingSid) {
104*77b80299SAndroid Build Coastguard Worker             return;
105*77b80299SAndroid Build Coastguard Worker         }
106*77b80299SAndroid Build Coastguard Worker 
107*77b80299SAndroid Build Coastguard Worker         e = getOrCreateExtras();
108*77b80299SAndroid Build Coastguard Worker         if (!e) return; // out of memory
109*77b80299SAndroid Build Coastguard Worker     }
110*77b80299SAndroid Build Coastguard Worker 
111*77b80299SAndroid Build Coastguard Worker     e->mRequestingSid = requestingSid;
112*77b80299SAndroid Build Coastguard Worker }
113*77b80299SAndroid Build Coastguard Worker 
transact(uint32_t code,const Parcel & data,Parcel * reply,uint32_t flags,TransactCallback callback)114*77b80299SAndroid Build Coastguard Worker status_t BHwBinder::transact(
115*77b80299SAndroid Build Coastguard Worker     uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags, TransactCallback callback)
116*77b80299SAndroid Build Coastguard Worker {
117*77b80299SAndroid Build Coastguard Worker     data.setDataPosition(0);
118*77b80299SAndroid Build Coastguard Worker 
119*77b80299SAndroid Build Coastguard Worker     if (reply != nullptr && (flags & FLAG_CLEAR_BUF)) {
120*77b80299SAndroid Build Coastguard Worker         reply->markSensitive();
121*77b80299SAndroid Build Coastguard Worker     }
122*77b80299SAndroid Build Coastguard Worker 
123*77b80299SAndroid Build Coastguard Worker     // extra comment to try to force running all tests
124*77b80299SAndroid Build Coastguard Worker     if (UNLIKELY(code == HIDL_DEBUG_TRANSACTION)) {
125*77b80299SAndroid Build Coastguard Worker         uid_t uid = IPCThreadState::self()->getCallingUid();
126*77b80299SAndroid Build Coastguard Worker         if (multiuser_get_app_id(uid) >= AID_APP_START) {
127*77b80299SAndroid Build Coastguard Worker             ALOGE("Can not call IBase::debug from apps");
128*77b80299SAndroid Build Coastguard Worker             return PERMISSION_DENIED;
129*77b80299SAndroid Build Coastguard Worker         }
130*77b80299SAndroid Build Coastguard Worker     }
131*77b80299SAndroid Build Coastguard Worker 
132*77b80299SAndroid Build Coastguard Worker     return onTransact(code, data, reply, flags, [&](auto& replyParcel) {
133*77b80299SAndroid Build Coastguard Worker       replyParcel.setDataPosition(0);
134*77b80299SAndroid Build Coastguard Worker       if (callback != nullptr) {
135*77b80299SAndroid Build Coastguard Worker         callback(replyParcel);
136*77b80299SAndroid Build Coastguard Worker       }
137*77b80299SAndroid Build Coastguard Worker     });
138*77b80299SAndroid Build Coastguard Worker }
139*77b80299SAndroid Build Coastguard Worker 
linkToDeath(const sp<DeathRecipient> &,void *,uint32_t)140*77b80299SAndroid Build Coastguard Worker status_t BHwBinder::linkToDeath(
141*77b80299SAndroid Build Coastguard Worker     const sp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
142*77b80299SAndroid Build Coastguard Worker     uint32_t /*flags*/)
143*77b80299SAndroid Build Coastguard Worker {
144*77b80299SAndroid Build Coastguard Worker     return INVALID_OPERATION;
145*77b80299SAndroid Build Coastguard Worker }
146*77b80299SAndroid Build Coastguard Worker 
unlinkToDeath(const wp<DeathRecipient> &,void *,uint32_t,wp<DeathRecipient> *)147*77b80299SAndroid Build Coastguard Worker status_t BHwBinder::unlinkToDeath(
148*77b80299SAndroid Build Coastguard Worker     const wp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
149*77b80299SAndroid Build Coastguard Worker     uint32_t /*flags*/, wp<DeathRecipient>* /*outRecipient*/)
150*77b80299SAndroid Build Coastguard Worker {
151*77b80299SAndroid Build Coastguard Worker     return INVALID_OPERATION;
152*77b80299SAndroid Build Coastguard Worker }
153*77b80299SAndroid Build Coastguard Worker 
attachObject(const void * objectID,void * object,void * cleanupCookie,object_cleanup_func func)154*77b80299SAndroid Build Coastguard Worker void BHwBinder::attachObject(
155*77b80299SAndroid Build Coastguard Worker     const void* objectID, void* object, void* cleanupCookie,
156*77b80299SAndroid Build Coastguard Worker     object_cleanup_func func)
157*77b80299SAndroid Build Coastguard Worker {
158*77b80299SAndroid Build Coastguard Worker     Extras* e = getOrCreateExtras();
159*77b80299SAndroid Build Coastguard Worker     if (!e) return; // out of memory
160*77b80299SAndroid Build Coastguard Worker 
161*77b80299SAndroid Build Coastguard Worker     AutoMutex _l(e->mLock);
162*77b80299SAndroid Build Coastguard Worker     e->mObjects.attach(objectID, object, cleanupCookie, func);
163*77b80299SAndroid Build Coastguard Worker }
164*77b80299SAndroid Build Coastguard Worker 
findObject(const void * objectID) const165*77b80299SAndroid Build Coastguard Worker void* BHwBinder::findObject(const void* objectID) const
166*77b80299SAndroid Build Coastguard Worker {
167*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_acquire);
168*77b80299SAndroid Build Coastguard Worker     if (!e) return nullptr;
169*77b80299SAndroid Build Coastguard Worker 
170*77b80299SAndroid Build Coastguard Worker     AutoMutex _l(e->mLock);
171*77b80299SAndroid Build Coastguard Worker     return e->mObjects.find(objectID);
172*77b80299SAndroid Build Coastguard Worker }
173*77b80299SAndroid Build Coastguard Worker 
detachObject(const void * objectID)174*77b80299SAndroid Build Coastguard Worker void BHwBinder::detachObject(const void* objectID)
175*77b80299SAndroid Build Coastguard Worker {
176*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_acquire);
177*77b80299SAndroid Build Coastguard Worker     if (!e) return;
178*77b80299SAndroid Build Coastguard Worker 
179*77b80299SAndroid Build Coastguard Worker     AutoMutex _l(e->mLock);
180*77b80299SAndroid Build Coastguard Worker     e->mObjects.detach(objectID);
181*77b80299SAndroid Build Coastguard Worker }
182*77b80299SAndroid Build Coastguard Worker 
localBinder()183*77b80299SAndroid Build Coastguard Worker BHwBinder* BHwBinder::localBinder()
184*77b80299SAndroid Build Coastguard Worker {
185*77b80299SAndroid Build Coastguard Worker     return this;
186*77b80299SAndroid Build Coastguard Worker }
187*77b80299SAndroid Build Coastguard Worker 
~BHwBinder()188*77b80299SAndroid Build Coastguard Worker BHwBinder::~BHwBinder()
189*77b80299SAndroid Build Coastguard Worker {
190*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_relaxed);
191*77b80299SAndroid Build Coastguard Worker     if (e) delete e;
192*77b80299SAndroid Build Coastguard Worker }
193*77b80299SAndroid Build Coastguard Worker 
194*77b80299SAndroid Build Coastguard Worker 
onTransact(uint32_t,const Parcel &,Parcel *,uint32_t,TransactCallback)195*77b80299SAndroid Build Coastguard Worker status_t BHwBinder::onTransact(
196*77b80299SAndroid Build Coastguard Worker     uint32_t /*code*/, const Parcel& /*data*/, Parcel* /*reply*/, uint32_t /*flags*/,
197*77b80299SAndroid Build Coastguard Worker     TransactCallback /*callback*/)
198*77b80299SAndroid Build Coastguard Worker {
199*77b80299SAndroid Build Coastguard Worker     return UNKNOWN_TRANSACTION;
200*77b80299SAndroid Build Coastguard Worker }
201*77b80299SAndroid Build Coastguard Worker 
getOrCreateExtras()202*77b80299SAndroid Build Coastguard Worker BHwBinder::Extras* BHwBinder::getOrCreateExtras()
203*77b80299SAndroid Build Coastguard Worker {
204*77b80299SAndroid Build Coastguard Worker     Extras* e = mExtras.load(std::memory_order_acquire);
205*77b80299SAndroid Build Coastguard Worker 
206*77b80299SAndroid Build Coastguard Worker     if (!e) {
207*77b80299SAndroid Build Coastguard Worker         e = new Extras;
208*77b80299SAndroid Build Coastguard Worker         Extras* expected = nullptr;
209*77b80299SAndroid Build Coastguard Worker         if (!mExtras.compare_exchange_strong(expected, e,
210*77b80299SAndroid Build Coastguard Worker                                              std::memory_order_release,
211*77b80299SAndroid Build Coastguard Worker                                              std::memory_order_acquire)) {
212*77b80299SAndroid Build Coastguard Worker             delete e;
213*77b80299SAndroid Build Coastguard Worker             e = expected;  // Filled in by CAS
214*77b80299SAndroid Build Coastguard Worker         }
215*77b80299SAndroid Build Coastguard Worker         if (e == nullptr) return nullptr; // out of memory
216*77b80299SAndroid Build Coastguard Worker     }
217*77b80299SAndroid Build Coastguard Worker 
218*77b80299SAndroid Build Coastguard Worker     return e;
219*77b80299SAndroid Build Coastguard Worker }
220*77b80299SAndroid Build Coastguard Worker 
221*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
222*77b80299SAndroid Build Coastguard Worker 
223*77b80299SAndroid Build Coastguard Worker enum {
224*77b80299SAndroid Build Coastguard Worker     // This is used to transfer ownership of the remote binder from
225*77b80299SAndroid Build Coastguard Worker     // the BpHwRefBase object holding it (when it is constructed), to the
226*77b80299SAndroid Build Coastguard Worker     // owner of the BpHwRefBase object when it first acquires that BpHwRefBase.
227*77b80299SAndroid Build Coastguard Worker     kRemoteAcquired = 0x00000001
228*77b80299SAndroid Build Coastguard Worker };
229*77b80299SAndroid Build Coastguard Worker 
BpHwRefBase(const sp<IBinder> & o)230*77b80299SAndroid Build Coastguard Worker BpHwRefBase::BpHwRefBase(const sp<IBinder>& o)
231*77b80299SAndroid Build Coastguard Worker     : mRemote(o.get()), mRefs(nullptr), mState(0)
232*77b80299SAndroid Build Coastguard Worker {
233*77b80299SAndroid Build Coastguard Worker     if (mRemote) {
234*77b80299SAndroid Build Coastguard Worker         mRemote->incStrong(this);           // Removed on first IncStrong().
235*77b80299SAndroid Build Coastguard Worker     }
236*77b80299SAndroid Build Coastguard Worker }
237*77b80299SAndroid Build Coastguard Worker 
~BpHwRefBase()238*77b80299SAndroid Build Coastguard Worker BpHwRefBase::~BpHwRefBase()
239*77b80299SAndroid Build Coastguard Worker {
240*77b80299SAndroid Build Coastguard Worker     if (mRemote) {
241*77b80299SAndroid Build Coastguard Worker         if (!(mState.load(std::memory_order_relaxed)&kRemoteAcquired)) {
242*77b80299SAndroid Build Coastguard Worker             mRemote->decStrong(this);
243*77b80299SAndroid Build Coastguard Worker         }
244*77b80299SAndroid Build Coastguard Worker     }
245*77b80299SAndroid Build Coastguard Worker }
246*77b80299SAndroid Build Coastguard Worker 
onFirstRef()247*77b80299SAndroid Build Coastguard Worker void BpHwRefBase::onFirstRef()
248*77b80299SAndroid Build Coastguard Worker {
249*77b80299SAndroid Build Coastguard Worker     mState.fetch_or(kRemoteAcquired, std::memory_order_relaxed);
250*77b80299SAndroid Build Coastguard Worker }
251*77b80299SAndroid Build Coastguard Worker 
onLastStrongRef(const void *)252*77b80299SAndroid Build Coastguard Worker void BpHwRefBase::onLastStrongRef(const void* /*id*/)
253*77b80299SAndroid Build Coastguard Worker {
254*77b80299SAndroid Build Coastguard Worker     if (mRemote) {
255*77b80299SAndroid Build Coastguard Worker         mRemote->decStrong(this);
256*77b80299SAndroid Build Coastguard Worker     }
257*77b80299SAndroid Build Coastguard Worker }
258*77b80299SAndroid Build Coastguard Worker 
onIncStrongAttempted(uint32_t,const void *)259*77b80299SAndroid Build Coastguard Worker bool BpHwRefBase::onIncStrongAttempted(uint32_t /*flags*/, const void* /*id*/)
260*77b80299SAndroid Build Coastguard Worker {
261*77b80299SAndroid Build Coastguard Worker     return false;
262*77b80299SAndroid Build Coastguard Worker }
263*77b80299SAndroid Build Coastguard Worker 
264*77b80299SAndroid Build Coastguard Worker // ---------------------------------------------------------------------------
265*77b80299SAndroid Build Coastguard Worker 
266*77b80299SAndroid Build Coastguard Worker } // namespace hardware
267*77b80299SAndroid Build Coastguard Worker } // namespace android
268