blob: c459d3f096ed04d658763cbe2730a92e1a365890 [file] [log] [blame]
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -08001/*
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
Mathias Agopianc5b2c0b2009-05-19 19:08:10 -070017#include <binder/Binder.h>
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -080018
Bailey Forrest6913c462015-08-18 17:15:10 -070019#include <atomic>
Dianne Hackborn555f89d2012-05-08 18:54:22 -070020#include <utils/misc.h>
Mathias Agopianc5b2c0b2009-05-19 19:08:10 -070021#include <binder/BpBinder.h>
22#include <binder/IInterface.h>
Dianne Hackborn23eb1e22015-10-07 17:35:27 -070023#include <binder/IResultReceiver.h>
Mathias Agopianc5b2c0b2009-05-19 19:08:10 -070024#include <binder/Parcel.h>
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -080025
26#include <stdio.h>
27
28namespace android {
29
30// ---------------------------------------------------------------------------
31
Mathias Agopian83c04462009-05-22 19:00:22 -070032IBinder::IBinder()
33 : RefBase()
34{
35}
36
37IBinder::~IBinder()
38{
39}
40
41// ---------------------------------------------------------------------------
42
Colin Cross6f4f3ab2014-02-05 17:42:44 -080043sp<IInterface> IBinder::queryLocalInterface(const String16& /*descriptor*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -080044{
45 return NULL;
46}
47
48BBinder* IBinder::localBinder()
49{
50 return NULL;
51}
52
53BpBinder* IBinder::remoteBinder()
54{
55 return NULL;
56}
57
58bool IBinder::checkSubclass(const void* /*subclassID*/) const
59{
60 return false;
61}
62
Dianne Hackborn23eb1e22015-10-07 17:35:27 -070063
64status_t IBinder::shellCommand(int /*in*/, int out, int /*err*/, Vector<String16>& /*args*/,
65 const sp<IResultReceiver>& resultReceiver)
66{
67 if (out >= 0) {
68 dprintf(out, "Shell commands not supported.\n");
69 }
70 if (resultReceiver != NULL) {
71 resultReceiver->send(INVALID_OPERATION);
72 }
73 return NO_ERROR;
74}
75
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -080076// ---------------------------------------------------------------------------
77
78class BBinder::Extras
79{
80public:
81 Mutex mLock;
82 BpBinder::ObjectManager mObjects;
83};
84
85// ---------------------------------------------------------------------------
86
Bailey Forrest6913c462015-08-18 17:15:10 -070087BBinder::BBinder() : mExtras(nullptr)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -080088{
89}
90
91bool BBinder::isBinderAlive() const
92{
93 return true;
94}
95
96status_t BBinder::pingBinder()
97{
98 return NO_ERROR;
99}
100
Mathias Agopian83c04462009-05-22 19:00:22 -0700101const String16& BBinder::getInterfaceDescriptor() const
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800102{
Dan Egnor386a3322010-05-06 00:55:09 -0700103 // This is a local static rather than a global static,
104 // to avoid static initializer ordering issues.
105 static String16 sEmptyDescriptor;
Steve Block32397c12012-01-05 23:22:43 +0000106 ALOGW("reached BBinder::getInterfaceDescriptor (this=%p)", this);
Mathias Agopian83c04462009-05-22 19:00:22 -0700107 return sEmptyDescriptor;
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800108}
109
110status_t BBinder::transact(
111 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
112{
113 data.setDataPosition(0);
114
115 status_t err = NO_ERROR;
116 switch (code) {
117 case PING_TRANSACTION:
118 reply->writeInt32(pingBinder());
119 break;
120 default:
121 err = onTransact(code, data, reply, flags);
122 break;
123 }
124
125 if (reply != NULL) {
126 reply->setDataPosition(0);
127 }
128
129 return err;
130}
131
132status_t BBinder::linkToDeath(
Colin Cross6f4f3ab2014-02-05 17:42:44 -0800133 const sp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
134 uint32_t /*flags*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800135{
136 return INVALID_OPERATION;
137}
138
139status_t BBinder::unlinkToDeath(
Colin Cross6f4f3ab2014-02-05 17:42:44 -0800140 const wp<DeathRecipient>& /*recipient*/, void* /*cookie*/,
141 uint32_t /*flags*/, wp<DeathRecipient>* /*outRecipient*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800142{
143 return INVALID_OPERATION;
144}
145
Dianne Hackborn23eb1e22015-10-07 17:35:27 -0700146status_t BBinder::dump(int /*fd*/, const Vector<String16>& /*args*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800147{
148 return NO_ERROR;
149}
150
151void BBinder::attachObject(
152 const void* objectID, void* object, void* cleanupCookie,
153 object_cleanup_func func)
154{
Bailey Forrest6913c462015-08-18 17:15:10 -0700155 Extras* e = mExtras.load(std::memory_order_acquire);
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800156
157 if (!e) {
158 e = new Extras;
Bailey Forrest6913c462015-08-18 17:15:10 -0700159 Extras* expected = nullptr;
160 if (!mExtras.compare_exchange_strong(expected, e,
161 std::memory_order_release,
162 std::memory_order_acquire)) {
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800163 delete e;
Bailey Forrest6913c462015-08-18 17:15:10 -0700164 e = expected; // Filled in by CAS
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800165 }
166 if (e == 0) return; // out of memory
167 }
168
169 AutoMutex _l(e->mLock);
170 e->mObjects.attach(objectID, object, cleanupCookie, func);
171}
172
173void* BBinder::findObject(const void* objectID) const
174{
Bailey Forrest6913c462015-08-18 17:15:10 -0700175 Extras* e = mExtras.load(std::memory_order_acquire);
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800176 if (!e) return NULL;
177
178 AutoMutex _l(e->mLock);
179 return e->mObjects.find(objectID);
180}
181
182void BBinder::detachObject(const void* objectID)
183{
Bailey Forrest6913c462015-08-18 17:15:10 -0700184 Extras* e = mExtras.load(std::memory_order_acquire);
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800185 if (!e) return;
186
187 AutoMutex _l(e->mLock);
188 e->mObjects.detach(objectID);
189}
190
191BBinder* BBinder::localBinder()
192{
193 return this;
194}
195
196BBinder::~BBinder()
197{
Bailey Forrest6913c462015-08-18 17:15:10 -0700198 Extras* e = mExtras.load(std::memory_order_relaxed);
Hans Boehm3effaba2014-08-12 22:56:00 +0000199 if (e) delete e;
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800200}
201
202
203status_t BBinder::onTransact(
Colin Cross6f4f3ab2014-02-05 17:42:44 -0800204 uint32_t code, const Parcel& data, Parcel* reply, uint32_t /*flags*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800205{
206 switch (code) {
207 case INTERFACE_TRANSACTION:
208 reply->writeString16(getInterfaceDescriptor());
209 return NO_ERROR;
210
211 case DUMP_TRANSACTION: {
212 int fd = data.readFileDescriptor();
213 int argc = data.readInt32();
214 Vector<String16> args;
215 for (int i = 0; i < argc && data.dataAvail() > 0; i++) {
216 args.add(data.readString16());
217 }
218 return dump(fd, args);
219 }
Dianne Hackborn555f89d2012-05-08 18:54:22 -0700220
Dianne Hackborn23eb1e22015-10-07 17:35:27 -0700221 case SHELL_COMMAND_TRANSACTION: {
222 int in = data.readFileDescriptor();
223 int out = data.readFileDescriptor();
224 int err = data.readFileDescriptor();
225 int argc = data.readInt32();
226 Vector<String16> args;
227 for (int i = 0; i < argc && data.dataAvail() > 0; i++) {
228 args.add(data.readString16());
229 }
230 sp<IResultReceiver> resultReceiver = IResultReceiver::asInterface(
231 data.readStrongBinder());
232
233 return shellCommand(in, out, err, args, resultReceiver);
234 }
235
Dianne Hackborn555f89d2012-05-08 18:54:22 -0700236 case SYSPROPS_TRANSACTION: {
237 report_sysprop_change();
238 return NO_ERROR;
239 }
240
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800241 default:
242 return UNKNOWN_TRANSACTION;
243 }
244}
245
246// ---------------------------------------------------------------------------
247
248enum {
249 // This is used to transfer ownership of the remote binder from
250 // the BpRefBase object holding it (when it is constructed), to the
251 // owner of the BpRefBase object when it first acquires that BpRefBase.
252 kRemoteAcquired = 0x00000001
253};
254
255BpRefBase::BpRefBase(const sp<IBinder>& o)
256 : mRemote(o.get()), mRefs(NULL), mState(0)
257{
258 extendObjectLifetime(OBJECT_LIFETIME_WEAK);
259
260 if (mRemote) {
261 mRemote->incStrong(this); // Removed on first IncStrong().
262 mRefs = mRemote->createWeak(this); // Held for our entire lifetime.
263 }
264}
265
266BpRefBase::~BpRefBase()
267{
268 if (mRemote) {
Bailey Forrest6913c462015-08-18 17:15:10 -0700269 if (!(mState.load(std::memory_order_relaxed)&kRemoteAcquired)) {
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800270 mRemote->decStrong(this);
271 }
272 mRefs->decWeak(this);
273 }
274}
275
276void BpRefBase::onFirstRef()
277{
Bailey Forrest6913c462015-08-18 17:15:10 -0700278 mState.fetch_or(kRemoteAcquired, std::memory_order_relaxed);
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800279}
280
Colin Cross6f4f3ab2014-02-05 17:42:44 -0800281void BpRefBase::onLastStrongRef(const void* /*id*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800282{
283 if (mRemote) {
284 mRemote->decStrong(this);
285 }
286}
287
Colin Cross6f4f3ab2014-02-05 17:42:44 -0800288bool BpRefBase::onIncStrongAttempted(uint32_t /*flags*/, const void* /*id*/)
The Android Open Source Projectedbf3b62009-03-03 19:31:44 -0800289{
290 return mRemote ? mRefs->attemptIncStrong(this) : false;
291}
292
293// ---------------------------------------------------------------------------
294
295}; // namespace android