blob: 9910d4fbd7b0e93b5e3597ae58810dfa43806e92 [file] [log] [blame]
Mathias Agopian7922fa22009-05-18 15:08:03 -07001/*
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
Steven Morelandc4dd2102017-02-23 13:57:21 -080017#define LOG_TAG "hw-IPCThreadState"
Jason Parks2b17f142009-11-03 12:14:38 -080018
Martijn Coenen4080edc2016-05-04 14:17:02 +020019#include <hwbinder/IPCThreadState.h>
Jayant Chowdhary985fc892018-10-01 22:54:05 +000020#include <binderthreadstate/IPCThreadStateBase.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070021
Martijn Coenen4080edc2016-05-04 14:17:02 +020022#include <hwbinder/Binder.h>
Yifan Hong1e118d22017-01-12 14:42:28 -080023#include <hwbinder/BpHwBinder.h>
Martijn Coenen4080edc2016-05-04 14:17:02 +020024#include <hwbinder/TextOutput.h>
Chia-I Wu0e72fd52016-10-06 14:20:41 +080025#include <hwbinder/binder_kernel.h>
Mathias Agopian4ea13dc2013-05-06 20:20:50 -070026
Steven Morelandd7bbfdb2018-05-01 16:30:46 -070027#include <android-base/macros.h>
Steven Moreland14603002019-01-02 17:54:16 -080028#include <utils/CallStack.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070029#include <utils/Log.h>
Colin Crossb1dc6542016-04-15 14:29:55 -070030#include <utils/SystemClock.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070031#include <utils/threads.h>
32
33#include <private/binder/binder_module.h>
Martijn Coenene01f4f22016-05-12 12:33:28 +020034#include <hwbinder/Static.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070035
Mathias Agopian7922fa22009-05-18 15:08:03 -070036#include <errno.h>
Colin Crossb1dc6542016-04-15 14:29:55 -070037#include <inttypes.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070038#include <pthread.h>
39#include <sched.h>
Yabin Cuibbef2ba2015-01-26 19:45:47 -080040#include <signal.h>
41#include <stdio.h>
42#include <sys/ioctl.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070043#include <sys/resource.h>
Yabin Cuibbef2ba2015-01-26 19:45:47 -080044#include <unistd.h>
Mathias Agopian7922fa22009-05-18 15:08:03 -070045
46#if LOG_NDEBUG
47
48#define IF_LOG_TRANSACTIONS() if (false)
49#define IF_LOG_COMMANDS() if (false)
Yifan Hongdde40f32017-01-12 14:22:45 -080050#define LOG_REMOTEREFS(...)
Mathias Agopian7922fa22009-05-18 15:08:03 -070051#define IF_LOG_REMOTEREFS() if (false)
Yifan Hongdde40f32017-01-12 14:22:45 -080052#define LOG_THREADPOOL(...)
53#define LOG_ONEWAY(...)
Mathias Agopian7922fa22009-05-18 15:08:03 -070054
55#else
56
Steve Block5854b912011-10-12 17:27:03 +010057#define IF_LOG_TRANSACTIONS() IF_ALOG(LOG_VERBOSE, "transact")
58#define IF_LOG_COMMANDS() IF_ALOG(LOG_VERBOSE, "ipc")
59#define LOG_REMOTEREFS(...) ALOG(LOG_DEBUG, "remoterefs", __VA_ARGS__)
60#define IF_LOG_REMOTEREFS() IF_ALOG(LOG_DEBUG, "remoterefs")
61#define LOG_THREADPOOL(...) ALOG(LOG_DEBUG, "threadpool", __VA_ARGS__)
62#define LOG_ONEWAY(...) ALOG(LOG_DEBUG, "ipc", __VA_ARGS__)
Mathias Agopian7922fa22009-05-18 15:08:03 -070063
64#endif
65
66// ---------------------------------------------------------------------------
67
68namespace android {
Martijn Coenenf75a23d2016-08-01 11:55:17 +020069namespace hardware {
Mathias Agopian7922fa22009-05-18 15:08:03 -070070
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -070071// Static const and functions will be optimized out if not used,
72// when LOG_NDEBUG and references in IF_LOG_COMMANDS() are optimized out.
Mathias Agopian7922fa22009-05-18 15:08:03 -070073static const char *kReturnStrings[] = {
Andy McFadden457d51f2011-08-31 07:43:40 -070074 "BR_ERROR",
Mathias Agopian7922fa22009-05-18 15:08:03 -070075 "BR_OK",
Mathias Agopian7922fa22009-05-18 15:08:03 -070076 "BR_TRANSACTION",
77 "BR_REPLY",
78 "BR_ACQUIRE_RESULT",
79 "BR_DEAD_REPLY",
80 "BR_TRANSACTION_COMPLETE",
81 "BR_INCREFS",
82 "BR_ACQUIRE",
83 "BR_RELEASE",
84 "BR_DECREFS",
85 "BR_ATTEMPT_ACQUIRE",
Mathias Agopian7922fa22009-05-18 15:08:03 -070086 "BR_NOOP",
87 "BR_SPAWN_LOOPER",
88 "BR_FINISHED",
89 "BR_DEAD_BINDER",
Andy McFadden457d51f2011-08-31 07:43:40 -070090 "BR_CLEAR_DEATH_NOTIFICATION_DONE",
91 "BR_FAILED_REPLY"
Mathias Agopian7922fa22009-05-18 15:08:03 -070092};
93
94static const char *kCommandStrings[] = {
Mathias Agopian7922fa22009-05-18 15:08:03 -070095 "BC_TRANSACTION",
96 "BC_REPLY",
97 "BC_ACQUIRE_RESULT",
98 "BC_FREE_BUFFER",
Mathias Agopian7922fa22009-05-18 15:08:03 -070099 "BC_INCREFS",
100 "BC_ACQUIRE",
101 "BC_RELEASE",
102 "BC_DECREFS",
103 "BC_INCREFS_DONE",
104 "BC_ACQUIRE_DONE",
105 "BC_ATTEMPT_ACQUIRE",
Mathias Agopian7922fa22009-05-18 15:08:03 -0700106 "BC_REGISTER_LOOPER",
107 "BC_ENTER_LOOPER",
108 "BC_EXIT_LOOPER",
Mathias Agopian7922fa22009-05-18 15:08:03 -0700109 "BC_REQUEST_DEATH_NOTIFICATION",
110 "BC_CLEAR_DEATH_NOTIFICATION",
111 "BC_DEAD_BINDER_DONE"
Mathias Agopian7922fa22009-05-18 15:08:03 -0700112};
113
114static const char* getReturnString(size_t idx)
115{
116 if (idx < sizeof(kReturnStrings) / sizeof(kReturnStrings[0]))
117 return kReturnStrings[idx];
118 else
119 return "unknown";
120}
121
Mathias Agopian7922fa22009-05-18 15:08:03 -0700122static const void* printBinderTransactionData(TextOutput& out, const void* data)
123{
124 const binder_transaction_data* btd =
125 (const binder_transaction_data*)data;
Andy McFadden457d51f2011-08-31 07:43:40 -0700126 if (btd->target.handle < 1024) {
127 /* want to print descriptors in decimal; guess based on value */
128 out << "target.desc=" << btd->target.handle;
129 } else {
130 out << "target.ptr=" << btd->target.ptr;
131 }
132 out << " (cookie " << btd->cookie << ")" << endl
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700133 << "code=" << TypeCode(btd->code) << ", flags=" << (void*)(long)btd->flags << endl
Mathias Agopian7922fa22009-05-18 15:08:03 -0700134 << "data=" << btd->data.ptr.buffer << " (" << (void*)btd->data_size
135 << " bytes)" << endl
136 << "offsets=" << btd->data.ptr.offsets << " (" << (void*)btd->offsets_size
Andy McFadden457d51f2011-08-31 07:43:40 -0700137 << " bytes)";
Mathias Agopian7922fa22009-05-18 15:08:03 -0700138 return btd+1;
139}
140
141static const void* printReturnCommand(TextOutput& out, const void* _cmd)
142{
Andy McFadden457d51f2011-08-31 07:43:40 -0700143 static const size_t N = sizeof(kReturnStrings)/sizeof(kReturnStrings[0]);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700144 const int32_t* cmd = (const int32_t*)_cmd;
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +0100145 uint32_t code = (uint32_t)*cmd++;
Andy McFadden457d51f2011-08-31 07:43:40 -0700146 size_t cmdIndex = code & 0xff;
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +0100147 if (code == BR_ERROR) {
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700148 out << "BR_ERROR: " << (void*)(long)(*cmd++) << endl;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700149 return cmd;
Andy McFadden457d51f2011-08-31 07:43:40 -0700150 } else if (cmdIndex >= N) {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700151 out << "Unknown reply: " << code << endl;
152 return cmd;
153 }
Andy McFadden457d51f2011-08-31 07:43:40 -0700154 out << kReturnStrings[cmdIndex];
Yifan Hongdde40f32017-01-12 14:22:45 -0800155
Mathias Agopian7922fa22009-05-18 15:08:03 -0700156 switch (code) {
157 case BR_TRANSACTION:
158 case BR_REPLY: {
159 out << ": " << indent;
160 cmd = (const int32_t *)printBinderTransactionData(out, cmd);
161 out << dedent;
162 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800163
Mathias Agopian7922fa22009-05-18 15:08:03 -0700164 case BR_ACQUIRE_RESULT: {
165 const int32_t res = *cmd++;
166 out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)");
167 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800168
Mathias Agopian7922fa22009-05-18 15:08:03 -0700169 case BR_INCREFS:
170 case BR_ACQUIRE:
171 case BR_RELEASE:
172 case BR_DECREFS: {
173 const int32_t b = *cmd++;
174 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700175 out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c << ")";
Mathias Agopian7922fa22009-05-18 15:08:03 -0700176 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800177
Mathias Agopian7922fa22009-05-18 15:08:03 -0700178 case BR_ATTEMPT_ACQUIRE: {
179 const int32_t p = *cmd++;
180 const int32_t b = *cmd++;
181 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700182 out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c
Mathias Agopian7922fa22009-05-18 15:08:03 -0700183 << "), pri=" << p;
184 } break;
185
186 case BR_DEAD_BINDER:
187 case BR_CLEAR_DEATH_NOTIFICATION_DONE: {
188 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700189 out << ": death cookie " << (void*)(long)c;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700190 } break;
Andy McFadden457d51f2011-08-31 07:43:40 -0700191
192 default:
193 // no details to show for: BR_OK, BR_DEAD_REPLY,
194 // BR_TRANSACTION_COMPLETE, BR_FINISHED
195 break;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700196 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800197
Mathias Agopian7922fa22009-05-18 15:08:03 -0700198 out << endl;
199 return cmd;
200}
201
202static const void* printCommand(TextOutput& out, const void* _cmd)
203{
Andy McFadden457d51f2011-08-31 07:43:40 -0700204 static const size_t N = sizeof(kCommandStrings)/sizeof(kCommandStrings[0]);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700205 const int32_t* cmd = (const int32_t*)_cmd;
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +0100206 uint32_t code = (uint32_t)*cmd++;
Andy McFadden457d51f2011-08-31 07:43:40 -0700207 size_t cmdIndex = code & 0xff;
208
209 if (cmdIndex >= N) {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700210 out << "Unknown command: " << code << endl;
211 return cmd;
212 }
Andy McFadden457d51f2011-08-31 07:43:40 -0700213 out << kCommandStrings[cmdIndex];
214
Mathias Agopian7922fa22009-05-18 15:08:03 -0700215 switch (code) {
216 case BC_TRANSACTION:
217 case BC_REPLY: {
218 out << ": " << indent;
219 cmd = (const int32_t *)printBinderTransactionData(out, cmd);
220 out << dedent;
221 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800222
Mathias Agopian7922fa22009-05-18 15:08:03 -0700223 case BC_ACQUIRE_RESULT: {
224 const int32_t res = *cmd++;
225 out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)");
226 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800227
Mathias Agopian7922fa22009-05-18 15:08:03 -0700228 case BC_FREE_BUFFER: {
229 const int32_t buf = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700230 out << ": buffer=" << (void*)(long)buf;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700231 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800232
Mathias Agopian7922fa22009-05-18 15:08:03 -0700233 case BC_INCREFS:
234 case BC_ACQUIRE:
235 case BC_RELEASE:
236 case BC_DECREFS: {
237 const int32_t d = *cmd++;
Andy McFadden457d51f2011-08-31 07:43:40 -0700238 out << ": desc=" << d;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700239 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800240
Mathias Agopian7922fa22009-05-18 15:08:03 -0700241 case BC_INCREFS_DONE:
242 case BC_ACQUIRE_DONE: {
243 const int32_t b = *cmd++;
244 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700245 out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c << ")";
Mathias Agopian7922fa22009-05-18 15:08:03 -0700246 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800247
Mathias Agopian7922fa22009-05-18 15:08:03 -0700248 case BC_ATTEMPT_ACQUIRE: {
249 const int32_t p = *cmd++;
250 const int32_t d = *cmd++;
Andy McFadden457d51f2011-08-31 07:43:40 -0700251 out << ": desc=" << d << ", pri=" << p;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700252 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800253
Mathias Agopian7922fa22009-05-18 15:08:03 -0700254 case BC_REQUEST_DEATH_NOTIFICATION:
255 case BC_CLEAR_DEATH_NOTIFICATION: {
256 const int32_t h = *cmd++;
257 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700258 out << ": handle=" << h << " (death cookie " << (void*)(long)c << ")";
Mathias Agopian7922fa22009-05-18 15:08:03 -0700259 } break;
260
261 case BC_DEAD_BINDER_DONE: {
262 const int32_t c = *cmd++;
Chih-Hung Hsieh30dcad72014-10-24 14:10:09 -0700263 out << ": death cookie " << (void*)(long)c;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700264 } break;
Andy McFadden457d51f2011-08-31 07:43:40 -0700265
266 default:
267 // no details to show for: BC_REGISTER_LOOPER, BC_ENTER_LOOPER,
268 // BC_EXIT_LOOPER
269 break;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700270 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800271
Mathias Agopian7922fa22009-05-18 15:08:03 -0700272 out << endl;
273 return cmd;
274}
Mathias Agopian7922fa22009-05-18 15:08:03 -0700275
276static pthread_mutex_t gTLSMutex = PTHREAD_MUTEX_INITIALIZER;
277static bool gHaveTLS = false;
278static pthread_key_t gTLS = 0;
279static bool gShutdown = false;
280
281IPCThreadState* IPCThreadState::self()
282{
283 if (gHaveTLS) {
284restart:
285 const pthread_key_t k = gTLS;
286 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k);
287 if (st) return st;
288 return new IPCThreadState;
289 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800290
Andreas Gampe1d5dc2b2016-02-01 13:21:56 -0800291 if (gShutdown) {
292 ALOGW("Calling IPCThreadState::self() during shutdown is dangerous, expect a crash.\n");
Yi Kong55d41072018-07-23 14:55:39 -0700293 return nullptr;
Andreas Gampe1d5dc2b2016-02-01 13:21:56 -0800294 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800295
Mathias Agopian7922fa22009-05-18 15:08:03 -0700296 pthread_mutex_lock(&gTLSMutex);
297 if (!gHaveTLS) {
Andreas Gampe1d5dc2b2016-02-01 13:21:56 -0800298 int key_create_value = pthread_key_create(&gTLS, threadDestructor);
299 if (key_create_value != 0) {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700300 pthread_mutex_unlock(&gTLSMutex);
Andreas Gampe1d5dc2b2016-02-01 13:21:56 -0800301 ALOGW("IPCThreadState::self() unable to create TLS key, expect a crash: %s\n",
302 strerror(key_create_value));
Yi Kong55d41072018-07-23 14:55:39 -0700303 return nullptr;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700304 }
305 gHaveTLS = true;
306 }
307 pthread_mutex_unlock(&gTLSMutex);
308 goto restart;
309}
310
Brad Fitzpatrick77949942010-12-13 16:52:35 -0800311IPCThreadState* IPCThreadState::selfOrNull()
312{
313 if (gHaveTLS) {
314 const pthread_key_t k = gTLS;
315 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k);
316 return st;
317 }
Yi Kong55d41072018-07-23 14:55:39 -0700318 return nullptr;
Brad Fitzpatrick77949942010-12-13 16:52:35 -0800319}
320
Mathias Agopian7922fa22009-05-18 15:08:03 -0700321void IPCThreadState::shutdown()
322{
323 gShutdown = true;
Yifan Hongdde40f32017-01-12 14:22:45 -0800324
Mathias Agopian7922fa22009-05-18 15:08:03 -0700325 if (gHaveTLS) {
326 // XXX Need to wait for all thread pool threads to exit!
327 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(gTLS);
328 if (st) {
329 delete st;
Yi Kong55d41072018-07-23 14:55:39 -0700330 pthread_setspecific(gTLS, nullptr);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700331 }
zhongjie8e8a0252016-03-09 15:05:04 +0800332 pthread_key_delete(gTLS);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700333 gHaveTLS = false;
334 }
335}
336
Steven Moreland8c3f4bd2018-05-07 15:45:23 -0700337// TODO(b/66905301): remove symbol
338void IPCThreadState::disableBackgroundScheduling(bool /* disable */) {}
Dianne Hackborn5f4d7e82009-12-07 17:59:37 -0800339
Mathias Agopian7922fa22009-05-18 15:08:03 -0700340sp<ProcessState> IPCThreadState::process()
341{
342 return mProcess;
343}
344
345status_t IPCThreadState::clearLastError()
346{
347 const status_t err = mLastError;
348 mLastError = NO_ERROR;
349 return err;
350}
351
Dan Stozae8da8a42014-11-26 12:23:23 -0800352pid_t IPCThreadState::getCallingPid() const
Mathias Agopian7922fa22009-05-18 15:08:03 -0700353{
354 return mCallingPid;
355}
356
Dan Stozae8da8a42014-11-26 12:23:23 -0800357uid_t IPCThreadState::getCallingUid() const
Mathias Agopian7922fa22009-05-18 15:08:03 -0700358{
359 return mCallingUid;
360}
361
362int64_t IPCThreadState::clearCallingIdentity()
363{
364 int64_t token = ((int64_t)mCallingUid<<32) | mCallingPid;
365 clearCaller();
366 return token;
367}
368
Brad Fitzpatrick94c36342010-06-18 13:07:53 -0700369void IPCThreadState::setStrictModePolicy(int32_t policy)
370{
371 mStrictModePolicy = policy;
372}
373
Brad Fitzpatrick3f4ef592010-07-07 16:06:39 -0700374int32_t IPCThreadState::getStrictModePolicy() const
375{
Brad Fitzpatrick94c36342010-06-18 13:07:53 -0700376 return mStrictModePolicy;
377}
378
Brad Fitzpatrick24f8bca2010-08-30 16:01:16 -0700379void IPCThreadState::setLastTransactionBinderFlags(int32_t flags)
380{
381 mLastTransactionBinderFlags = flags;
382}
383
384int32_t IPCThreadState::getLastTransactionBinderFlags() const
385{
386 return mLastTransactionBinderFlags;
387}
388
Mathias Agopian7922fa22009-05-18 15:08:03 -0700389void IPCThreadState::restoreCallingIdentity(int64_t token)
390{
391 mCallingUid = (int)(token>>32);
392 mCallingPid = (int)token;
393}
394
395void IPCThreadState::clearCaller()
396{
Marco Nelissenb4f35d02009-07-17 07:59:17 -0700397 mCallingPid = getpid();
398 mCallingUid = getuid();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700399}
400
401void IPCThreadState::flushCommands()
402{
403 if (mProcess->mDriverFD <= 0)
404 return;
405 talkWithDriver(false);
Martijn Coenenb8253722018-05-23 15:33:22 +0200406 // The flush could have caused post-write refcount decrements to have
407 // been executed, which in turn could result in BC_RELEASE/BC_DECREFS
408 // being queued in mOut. So flush again, if we need to.
409 if (mOut.dataSize() > 0) {
410 talkWithDriver(false);
411 }
412 if (mOut.dataSize() > 0) {
413 ALOGW("mOut.dataSize() > 0 after flushCommands()");
414 }
Mathias Agopian7922fa22009-05-18 15:08:03 -0700415}
416
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700417void IPCThreadState::blockUntilThreadAvailable()
418{
419 pthread_mutex_lock(&mProcess->mThreadCountLock);
420 while (mProcess->mExecutingThreadsCount >= mProcess->mMaxThreads) {
Wale Ogunwale319900a2015-04-21 12:29:50 -0700421 ALOGW("Waiting for thread to be free. mExecutingThreadsCount=%lu mMaxThreads=%lu\n",
422 static_cast<unsigned long>(mProcess->mExecutingThreadsCount),
423 static_cast<unsigned long>(mProcess->mMaxThreads));
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700424 pthread_cond_wait(&mProcess->mThreadCountDecrement, &mProcess->mThreadCountLock);
425 }
426 pthread_mutex_unlock(&mProcess->mThreadCountLock);
427}
428
Todd Poynor0646cb02013-06-25 19:12:18 -0700429status_t IPCThreadState::getAndExecuteCommand()
430{
431 status_t result;
432 int32_t cmd;
433
434 result = talkWithDriver();
435 if (result >= NO_ERROR) {
436 size_t IN = mIn.dataAvail();
437 if (IN < sizeof(int32_t)) return result;
438 cmd = mIn.readInt32();
439 IF_LOG_COMMANDS() {
440 alog << "Processing top-level Command: "
441 << getReturnString(cmd) << endl;
442 }
443
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700444 pthread_mutex_lock(&mProcess->mThreadCountLock);
445 mProcess->mExecutingThreadsCount++;
Colin Crossb1dc6542016-04-15 14:29:55 -0700446 if (mProcess->mExecutingThreadsCount >= mProcess->mMaxThreads &&
Martijn Coenen0ce07ce2017-07-14 15:37:25 +0200447 mProcess->mMaxThreads > 1 && mProcess->mStarvationStartTimeMs == 0) {
Colin Crossb1dc6542016-04-15 14:29:55 -0700448 mProcess->mStarvationStartTimeMs = uptimeMillis();
449 }
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700450 pthread_mutex_unlock(&mProcess->mThreadCountLock);
451
Todd Poynor0646cb02013-06-25 19:12:18 -0700452 result = executeCommand(cmd);
453
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700454 pthread_mutex_lock(&mProcess->mThreadCountLock);
455 mProcess->mExecutingThreadsCount--;
Wei Wangdf7f40d2018-03-29 15:41:59 -0700456 if (mProcess->mExecutingThreadsCount < mProcess->mMaxThreads &&
Martijn Coenen0ce07ce2017-07-14 15:37:25 +0200457 mProcess->mStarvationStartTimeMs != 0) {
Colin Crossb1dc6542016-04-15 14:29:55 -0700458 int64_t starvationTimeMs = uptimeMillis() - mProcess->mStarvationStartTimeMs;
459 if (starvationTimeMs > 100) {
Wei Wangdf7f40d2018-03-29 15:41:59 -0700460 // If there is only a single-threaded client, nobody would be blocked
461 // on this, and it's not really starvation. (see b/37647467)
462 ALOGW("All binder threads in pool (%zu threads) busy for %" PRId64 " ms%s",
463 mProcess->mMaxThreads, starvationTimeMs,
464 mProcess->mMaxThreads > 1 ? "" : " (may be a false alarm)");
Colin Crossb1dc6542016-04-15 14:29:55 -0700465 }
466 mProcess->mStarvationStartTimeMs = 0;
467 }
Wale Ogunwale2e604f02015-04-13 16:16:10 -0700468 pthread_cond_broadcast(&mProcess->mThreadCountDecrement);
469 pthread_mutex_unlock(&mProcess->mThreadCountLock);
Todd Poynor0646cb02013-06-25 19:12:18 -0700470 }
471
Steven Morelandd7bbfdb2018-05-01 16:30:46 -0700472 if (UNLIKELY(!mPostCommandTasks.empty())) {
473 // make a copy in case the post transaction task makes a binder
474 // call and that other process calls back into us
475 std::vector<std::function<void(void)>> tasks = mPostCommandTasks;
476 mPostCommandTasks.clear();
Chih-Hung Hsiehe8675522018-12-12 14:42:24 -0800477 for (const auto& func : tasks) {
Steven Morelandd7bbfdb2018-05-01 16:30:46 -0700478 func();
479 }
480 }
481
Todd Poynor0646cb02013-06-25 19:12:18 -0700482 return result;
483}
484
485// When we've cleared the incoming command queue, process any pending derefs
486void IPCThreadState::processPendingDerefs()
487{
488 if (mIn.dataPosition() >= mIn.dataSize()) {
Martijn Coenenc9f105b2017-08-08 15:36:16 +0200489 /*
490 * The decWeak()/decStrong() calls may cause a destructor to run,
491 * which in turn could have initiated an outgoing transaction,
492 * which in turn could cause us to add to the pending refs
493 * vectors; so instead of simply iterating, loop until they're empty.
494 *
495 * We do this in an outer loop, because calling decStrong()
496 * may result in something being added to mPendingWeakDerefs,
497 * which could be delayed until the next incoming command
498 * from the driver if we don't process it now.
499 */
500 while (mPendingWeakDerefs.size() > 0 || mPendingStrongDerefs.size() > 0) {
501 while (mPendingWeakDerefs.size() > 0) {
502 RefBase::weakref_type* refs = mPendingWeakDerefs[0];
503 mPendingWeakDerefs.removeAt(0);
Todd Poynor0646cb02013-06-25 19:12:18 -0700504 refs->decWeak(mProcess.get());
505 }
Todd Poynor0646cb02013-06-25 19:12:18 -0700506
Martijn Coenenc9f105b2017-08-08 15:36:16 +0200507 if (mPendingStrongDerefs.size() > 0) {
508 // We don't use while() here because we don't want to re-order
509 // strong and weak decs at all; if this decStrong() causes both a
510 // decWeak() and a decStrong() to be queued, we want to process
511 // the decWeak() first.
512 BHwBinder* obj = mPendingStrongDerefs[0];
513 mPendingStrongDerefs.removeAt(0);
Todd Poynor0646cb02013-06-25 19:12:18 -0700514 obj->decStrong(mProcess.get());
515 }
Todd Poynor0646cb02013-06-25 19:12:18 -0700516 }
517 }
518}
519
Martijn Coenenb8253722018-05-23 15:33:22 +0200520void IPCThreadState::processPostWriteDerefs()
521{
522 /*
523 * libhwbinder has a flushCommands() in the BpHwBinder destructor,
524 * which makes this function (potentially) reentrant.
525 * New entries shouldn't be added though, so just iterating until empty
526 * should be safe.
527 */
528 while (mPostWriteWeakDerefs.size() > 0) {
529 RefBase::weakref_type* refs = mPostWriteWeakDerefs[0];
530 mPostWriteWeakDerefs.removeAt(0);
531 refs->decWeak(mProcess.get());
532 }
533
534 while (mPostWriteStrongDerefs.size() > 0) {
535 RefBase* obj = mPostWriteStrongDerefs[0];
536 mPostWriteStrongDerefs.removeAt(0);
537 obj->decStrong(mProcess.get());
538 }
539}
540
Mathias Agopian7922fa22009-05-18 15:08:03 -0700541void IPCThreadState::joinThreadPool(bool isMain)
542{
543 LOG_THREADPOOL("**** THREAD %p (PID %d) IS JOINING THE THREAD POOL\n", (void*)pthread_self(), getpid());
544
545 mOut.writeInt32(isMain ? BC_ENTER_LOOPER : BC_REGISTER_LOOPER);
Yifan Hongdde40f32017-01-12 14:22:45 -0800546
Mathias Agopian7922fa22009-05-18 15:08:03 -0700547 status_t result;
Martijn Coenen420d4bb2017-10-24 11:43:55 +0200548 mIsLooper = true;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700549 do {
Todd Poynor0646cb02013-06-25 19:12:18 -0700550 processPendingDerefs();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700551 // now get the next command to be processed, waiting if necessary
Todd Poynor0646cb02013-06-25 19:12:18 -0700552 result = getAndExecuteCommand();
Jason Parks2b17f142009-11-03 12:14:38 -0800553
Todd Poynor0646cb02013-06-25 19:12:18 -0700554 if (result < NO_ERROR && result != TIMED_OUT && result != -ECONNREFUSED && result != -EBADF) {
555 ALOGE("getAndExecuteCommand(fd=%d) returned unexpected error %d, aborting",
Jeff Tinkeree711ec2013-06-11 11:30:21 -0700556 mProcess->mDriverFD, result);
557 abort();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700558 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800559
Mathias Agopian7922fa22009-05-18 15:08:03 -0700560 // Let this thread exit the thread pool if it is no longer
561 // needed and it is not the main process thread.
562 if(result == TIMED_OUT && !isMain) {
563 break;
564 }
565 } while (result != -ECONNREFUSED && result != -EBADF);
566
Wei Wang8a2e8ac2016-10-14 09:54:27 -0700567 LOG_THREADPOOL("**** THREAD %p (PID %d) IS LEAVING THE THREAD POOL err=%d\n",
568 (void*)pthread_self(), getpid(), result);
Yifan Hongdde40f32017-01-12 14:22:45 -0800569
Mathias Agopian7922fa22009-05-18 15:08:03 -0700570 mOut.writeInt32(BC_EXIT_LOOPER);
Martijn Coenen420d4bb2017-10-24 11:43:55 +0200571 mIsLooper = false;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700572 talkWithDriver(false);
573}
574
Todd Poynor0646cb02013-06-25 19:12:18 -0700575int IPCThreadState::setupPolling(int* fd)
576{
577 if (mProcess->mDriverFD <= 0) {
578 return -EBADF;
579 }
580
Martijn Coenen80b88ab2017-09-25 14:50:05 +0200581 // Tells the kernel to not spawn any additional binder threads,
582 // as that won't work with polling. Also, the caller is responsible
583 // for subsequently calling handlePolledCommands()
584 mProcess->setThreadPoolConfiguration(1, true /* callerWillJoin */);
Tobias Lindskoga36d5762018-01-05 10:28:31 +0100585 mIsPollingThread = true;
Martijn Coenen80b88ab2017-09-25 14:50:05 +0200586
Todd Poynor0646cb02013-06-25 19:12:18 -0700587 mOut.writeInt32(BC_ENTER_LOOPER);
588 *fd = mProcess->mDriverFD;
589 return 0;
590}
591
592status_t IPCThreadState::handlePolledCommands()
593{
594 status_t result;
595
596 do {
597 result = getAndExecuteCommand();
598 } while (mIn.dataPosition() < mIn.dataSize());
599
600 processPendingDerefs();
601 flushCommands();
602 return result;
603}
604
Colin Crossf0487982014-02-05 17:42:44 -0800605void IPCThreadState::stopProcess(bool /*immediate*/)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700606{
Steve Block93cf8542012-01-04 20:05:49 +0000607 //ALOGI("**** STOPPING PROCESS");
Mathias Agopian7922fa22009-05-18 15:08:03 -0700608 flushCommands();
609 int fd = mProcess->mDriverFD;
610 mProcess->mDriverFD = -1;
611 close(fd);
612 //kill(getpid(), SIGKILL);
613}
614
615status_t IPCThreadState::transact(int32_t handle,
616 uint32_t code, const Parcel& data,
617 Parcel* reply, uint32_t flags)
618{
Ganesh Mahendrance45b892017-10-11 18:05:13 +0800619 status_t err;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700620
621 flags |= TF_ACCEPT_FDS;
622
623 IF_LOG_TRANSACTIONS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700624 alog << "BC_TRANSACTION thr " << (void*)pthread_self() << " / hand "
625 << handle << " / code " << TypeCode(code) << ": "
626 << indent << data << dedent << endl;
627 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800628
Ganesh Mahendrance45b892017-10-11 18:05:13 +0800629 LOG_ONEWAY(">>>> SEND from pid %d uid %d %s", getpid(), getuid(),
630 (flags & TF_ONE_WAY) == 0 ? "READ REPLY" : "ONE WAY");
Yi Kong55d41072018-07-23 14:55:39 -0700631 err = writeTransactionData(BC_TRANSACTION_SG, flags, handle, code, data, nullptr);
Yifan Hongdde40f32017-01-12 14:22:45 -0800632
Mathias Agopian7922fa22009-05-18 15:08:03 -0700633 if (err != NO_ERROR) {
634 if (reply) reply->setError(err);
635 return (mLastError = err);
636 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800637
Mathias Agopian7922fa22009-05-18 15:08:03 -0700638 if ((flags & TF_ONE_WAY) == 0) {
Steven Moreland14603002019-01-02 17:54:16 -0800639 if (UNLIKELY(mCallRestriction != ProcessState::CallRestriction::NONE)) {
640 if (mCallRestriction == ProcessState::CallRestriction::ERROR_IF_NOT_ONEWAY) {
641 ALOGE("Process making non-oneway call but is restricted.");
642 CallStack::logStack("non-oneway call", CallStack::getCurrent(10).get(),
643 ANDROID_LOG_ERROR);
644 } else /* FATAL_IF_NOT_ONEWAY */ {
645 LOG_ALWAYS_FATAL("Process may not make oneway calls.");
646 }
647 }
648
Dianne Hackborn98878262010-09-24 11:16:23 -0700649 #if 0
650 if (code == 4) { // relayout
Steve Block93cf8542012-01-04 20:05:49 +0000651 ALOGI(">>>>>> CALLING transaction 4");
Dianne Hackborn98878262010-09-24 11:16:23 -0700652 } else {
Steve Block93cf8542012-01-04 20:05:49 +0000653 ALOGI(">>>>>> CALLING transaction %d", code);
Dianne Hackborn98878262010-09-24 11:16:23 -0700654 }
655 #endif
Mathias Agopian7922fa22009-05-18 15:08:03 -0700656 if (reply) {
657 err = waitForResponse(reply);
658 } else {
659 Parcel fakeReply;
660 err = waitForResponse(&fakeReply);
661 }
Dianne Hackborn98878262010-09-24 11:16:23 -0700662 #if 0
663 if (code == 4) { // relayout
Steve Block93cf8542012-01-04 20:05:49 +0000664 ALOGI("<<<<<< RETURNING transaction 4");
Dianne Hackborn98878262010-09-24 11:16:23 -0700665 } else {
Steve Block93cf8542012-01-04 20:05:49 +0000666 ALOGI("<<<<<< RETURNING transaction %d", code);
Dianne Hackborn98878262010-09-24 11:16:23 -0700667 }
668 #endif
Yifan Hongdde40f32017-01-12 14:22:45 -0800669
Mathias Agopian7922fa22009-05-18 15:08:03 -0700670 IF_LOG_TRANSACTIONS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700671 alog << "BR_REPLY thr " << (void*)pthread_self() << " / hand "
672 << handle << ": ";
673 if (reply) alog << indent << *reply << dedent << endl;
674 else alog << "(none requested)" << endl;
675 }
676 } else {
Yi Kong55d41072018-07-23 14:55:39 -0700677 err = waitForResponse(nullptr, nullptr);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700678 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800679
Mathias Agopian7922fa22009-05-18 15:08:03 -0700680 return err;
681}
682
Martijn Coenenb8253722018-05-23 15:33:22 +0200683void IPCThreadState::incStrongHandle(int32_t handle, BpHwBinder *proxy)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700684{
685 LOG_REMOTEREFS("IPCThreadState::incStrongHandle(%d)\n", handle);
686 mOut.writeInt32(BC_ACQUIRE);
687 mOut.writeInt32(handle);
Martijn Coenenb8253722018-05-23 15:33:22 +0200688 // Create a temp reference until the driver has handled this command.
689 proxy->incStrong(mProcess.get());
690 mPostWriteStrongDerefs.push(proxy);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700691}
692
693void IPCThreadState::decStrongHandle(int32_t handle)
694{
695 LOG_REMOTEREFS("IPCThreadState::decStrongHandle(%d)\n", handle);
696 mOut.writeInt32(BC_RELEASE);
697 mOut.writeInt32(handle);
698}
699
Martijn Coenenb8253722018-05-23 15:33:22 +0200700void IPCThreadState::incWeakHandle(int32_t handle, BpHwBinder *proxy)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700701{
702 LOG_REMOTEREFS("IPCThreadState::incWeakHandle(%d)\n", handle);
703 mOut.writeInt32(BC_INCREFS);
704 mOut.writeInt32(handle);
Martijn Coenenb8253722018-05-23 15:33:22 +0200705 // Create a temp reference until the driver has handled this command.
706 proxy->getWeakRefs()->incWeak(mProcess.get());
707 mPostWriteWeakDerefs.push(proxy->getWeakRefs());
Mathias Agopian7922fa22009-05-18 15:08:03 -0700708}
709
710void IPCThreadState::decWeakHandle(int32_t handle)
711{
712 LOG_REMOTEREFS("IPCThreadState::decWeakHandle(%d)\n", handle);
713 mOut.writeInt32(BC_DECREFS);
714 mOut.writeInt32(handle);
715}
716
717status_t IPCThreadState::attemptIncStrongHandle(int32_t handle)
718{
Arve Hjønnevåg304dcae2014-02-14 20:14:02 -0800719#if HAS_BC_ATTEMPT_ACQUIRE
Andy McFadden457d51f2011-08-31 07:43:40 -0700720 LOG_REMOTEREFS("IPCThreadState::attemptIncStrongHandle(%d)\n", handle);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700721 mOut.writeInt32(BC_ATTEMPT_ACQUIRE);
722 mOut.writeInt32(0); // xxx was thread priority
723 mOut.writeInt32(handle);
724 status_t result = UNKNOWN_ERROR;
Yifan Hongdde40f32017-01-12 14:22:45 -0800725
Yi Kong55d41072018-07-23 14:55:39 -0700726 waitForResponse(nullptr, &result);
Yifan Hongdde40f32017-01-12 14:22:45 -0800727
Mathias Agopian7922fa22009-05-18 15:08:03 -0700728#if LOG_REFCOUNTS
729 printf("IPCThreadState::attemptIncStrongHandle(%ld) = %s\n",
730 handle, result == NO_ERROR ? "SUCCESS" : "FAILURE");
731#endif
Yifan Hongdde40f32017-01-12 14:22:45 -0800732
Mathias Agopian7922fa22009-05-18 15:08:03 -0700733 return result;
Arve Hjønnevåg304dcae2014-02-14 20:14:02 -0800734#else
735 (void)handle;
736 ALOGE("%s(%d): Not supported\n", __func__, handle);
737 return INVALID_OPERATION;
738#endif
Mathias Agopian7922fa22009-05-18 15:08:03 -0700739}
740
741void IPCThreadState::expungeHandle(int32_t handle, IBinder* binder)
742{
743#if LOG_REFCOUNTS
744 printf("IPCThreadState::expungeHandle(%ld)\n", handle);
745#endif
Yunlian Jiang6b65ac32017-09-19 15:51:07 -0700746 self()->mProcess->expungeHandle(handle, binder); // NOLINT
Mathias Agopian7922fa22009-05-18 15:08:03 -0700747}
748
Yifan Hong1e118d22017-01-12 14:42:28 -0800749status_t IPCThreadState::requestDeathNotification(int32_t handle, BpHwBinder* proxy)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700750{
751 mOut.writeInt32(BC_REQUEST_DEATH_NOTIFICATION);
752 mOut.writeInt32((int32_t)handle);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +0000753 mOut.writePointer((uintptr_t)proxy);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700754 return NO_ERROR;
755}
756
Yifan Hong1e118d22017-01-12 14:42:28 -0800757status_t IPCThreadState::clearDeathNotification(int32_t handle, BpHwBinder* proxy)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700758{
759 mOut.writeInt32(BC_CLEAR_DEATH_NOTIFICATION);
760 mOut.writeInt32((int32_t)handle);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +0000761 mOut.writePointer((uintptr_t)proxy);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700762 return NO_ERROR;
763}
764
765IPCThreadState::IPCThreadState()
Brad Fitzpatrick24f8bca2010-08-30 16:01:16 -0700766 : mProcess(ProcessState::self()),
Elliott Hughes07cf48a2014-08-18 10:38:38 -0700767 mMyThreadId(gettid()),
Brad Fitzpatrick24f8bca2010-08-30 16:01:16 -0700768 mStrictModePolicy(0),
Martijn Coenen9bd3d3b2017-12-12 09:29:14 +0100769 mLastTransactionBinderFlags(0),
Tobias Lindskoga36d5762018-01-05 10:28:31 +0100770 mIsLooper(false),
Steven Moreland14603002019-01-02 17:54:16 -0800771 mIsPollingThread(false),
772 mCallRestriction(mProcess->mCallRestriction) {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700773 pthread_setspecific(gTLS, this);
Dianne Hackborn5f4d7e82009-12-07 17:59:37 -0800774 clearCaller();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700775 mIn.setDataCapacity(256);
776 mOut.setDataCapacity(256);
Chih-Hung Hsieh29dbdcf2017-10-02 10:42:37 -0700777
778 // TODO(b/67742352): remove this variable from the class
779 (void)mMyThreadId;
Jayant Chowdhary985fc892018-10-01 22:54:05 +0000780 mIPCThreadStateBase = IPCThreadStateBase::self();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700781}
782
783IPCThreadState::~IPCThreadState()
784{
785}
786
787status_t IPCThreadState::sendReply(const Parcel& reply, uint32_t flags)
788{
789 status_t err;
790 status_t statusBuffer;
Martijn Coenend39a1682016-06-03 21:27:28 +0200791 err = writeTransactionData(BC_REPLY_SG, flags, -1, 0, reply, &statusBuffer);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700792 if (err < NO_ERROR) return err;
Yifan Hongdde40f32017-01-12 14:22:45 -0800793
Yi Kong55d41072018-07-23 14:55:39 -0700794 return waitForResponse(nullptr, nullptr);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700795}
796
797status_t IPCThreadState::waitForResponse(Parcel *reply, status_t *acquireResult)
798{
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +0100799 uint32_t cmd;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700800 int32_t err;
801
802 while (1) {
803 if ((err=talkWithDriver()) < NO_ERROR) break;
804 err = mIn.errorCheck();
805 if (err < NO_ERROR) break;
806 if (mIn.dataAvail() == 0) continue;
Yifan Hongdde40f32017-01-12 14:22:45 -0800807
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +0100808 cmd = (uint32_t)mIn.readInt32();
Yifan Hongdde40f32017-01-12 14:22:45 -0800809
Mathias Agopian7922fa22009-05-18 15:08:03 -0700810 IF_LOG_COMMANDS() {
811 alog << "Processing waitForResponse Command: "
812 << getReturnString(cmd) << endl;
813 }
814
815 switch (cmd) {
816 case BR_TRANSACTION_COMPLETE:
817 if (!reply && !acquireResult) goto finish;
818 break;
Yifan Hongdde40f32017-01-12 14:22:45 -0800819
Mathias Agopian7922fa22009-05-18 15:08:03 -0700820 case BR_DEAD_REPLY:
821 err = DEAD_OBJECT;
822 goto finish;
823
824 case BR_FAILED_REPLY:
825 err = FAILED_TRANSACTION;
826 goto finish;
Yifan Hongdde40f32017-01-12 14:22:45 -0800827
Mathias Agopian7922fa22009-05-18 15:08:03 -0700828 case BR_ACQUIRE_RESULT:
829 {
Yi Kong55d41072018-07-23 14:55:39 -0700830 ALOG_ASSERT(acquireResult != nullptr, "Unexpected brACQUIRE_RESULT");
Mathias Agopian7922fa22009-05-18 15:08:03 -0700831 const int32_t result = mIn.readInt32();
832 if (!acquireResult) continue;
833 *acquireResult = result ? NO_ERROR : INVALID_OPERATION;
834 }
835 goto finish;
Yifan Hongdde40f32017-01-12 14:22:45 -0800836
Mathias Agopian7922fa22009-05-18 15:08:03 -0700837 case BR_REPLY:
838 {
839 binder_transaction_data tr;
840 err = mIn.read(&tr, sizeof(tr));
Steve Blockd0bfabc2012-01-09 18:35:44 +0000841 ALOG_ASSERT(err == NO_ERROR, "Not enough command data for brREPLY");
Mathias Agopian7922fa22009-05-18 15:08:03 -0700842 if (err != NO_ERROR) goto finish;
843
844 if (reply) {
845 if ((tr.flags & TF_STATUS_CODE) == 0) {
846 reply->ipcSetDataReference(
847 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
848 tr.data_size,
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800849 reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
850 tr.offsets_size/sizeof(binder_size_t),
Mathias Agopian7922fa22009-05-18 15:08:03 -0700851 freeBuffer, this);
852 } else {
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800853 err = *reinterpret_cast<const status_t*>(tr.data.ptr.buffer);
Yi Kong55d41072018-07-23 14:55:39 -0700854 freeBuffer(nullptr,
Mathias Agopian7922fa22009-05-18 15:08:03 -0700855 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
856 tr.data_size,
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800857 reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
858 tr.offsets_size/sizeof(binder_size_t), this);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700859 }
860 } else {
Yi Kong55d41072018-07-23 14:55:39 -0700861 freeBuffer(nullptr,
Mathias Agopian7922fa22009-05-18 15:08:03 -0700862 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
863 tr.data_size,
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800864 reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
865 tr.offsets_size/sizeof(binder_size_t), this);
Mathias Agopian7922fa22009-05-18 15:08:03 -0700866 continue;
867 }
868 }
869 goto finish;
870
871 default:
872 err = executeCommand(cmd);
873 if (err != NO_ERROR) goto finish;
874 break;
875 }
876 }
877
878finish:
879 if (err != NO_ERROR) {
880 if (acquireResult) *acquireResult = err;
881 if (reply) reply->setError(err);
882 mLastError = err;
883 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800884
Mathias Agopian7922fa22009-05-18 15:08:03 -0700885 return err;
886}
887
888status_t IPCThreadState::talkWithDriver(bool doReceive)
889{
Johannes Carlsson597a3c72011-02-17 14:06:53 +0100890 if (mProcess->mDriverFD <= 0) {
891 return -EBADF;
892 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800893
Mathias Agopian7922fa22009-05-18 15:08:03 -0700894 binder_write_read bwr;
Yifan Hongdde40f32017-01-12 14:22:45 -0800895
Mathias Agopian7922fa22009-05-18 15:08:03 -0700896 // Is the read buffer empty?
897 const bool needRead = mIn.dataPosition() >= mIn.dataSize();
Yifan Hongdde40f32017-01-12 14:22:45 -0800898
Mathias Agopian7922fa22009-05-18 15:08:03 -0700899 // We don't want to write anything if we are still reading
900 // from data left in the input buffer and the caller
901 // has requested to read the next data.
902 const size_t outAvail = (!doReceive || needRead) ? mOut.dataSize() : 0;
Yifan Hongdde40f32017-01-12 14:22:45 -0800903
Mathias Agopian7922fa22009-05-18 15:08:03 -0700904 bwr.write_size = outAvail;
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800905 bwr.write_buffer = (uintptr_t)mOut.data();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700906
907 // This is what we'll read.
908 if (doReceive && needRead) {
909 bwr.read_size = mIn.dataCapacity();
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800910 bwr.read_buffer = (uintptr_t)mIn.data();
Mathias Agopian7922fa22009-05-18 15:08:03 -0700911 } else {
912 bwr.read_size = 0;
Ben Cheng455a70a2011-12-01 17:11:32 -0800913 bwr.read_buffer = 0;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700914 }
Andy McFadden457d51f2011-08-31 07:43:40 -0700915
Mathias Agopian7922fa22009-05-18 15:08:03 -0700916 IF_LOG_COMMANDS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700917 if (outAvail != 0) {
918 alog << "Sending commands to driver: " << indent;
919 const void* cmds = (const void*)bwr.write_buffer;
920 const void* end = ((const uint8_t*)cmds)+bwr.write_size;
921 alog << HexDump(cmds, bwr.write_size) << endl;
922 while (cmds < end) cmds = printCommand(alog, cmds);
923 alog << dedent;
924 }
925 alog << "Size of receive buffer: " << bwr.read_size
926 << ", needRead: " << needRead << ", doReceive: " << doReceive << endl;
927 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800928
Mathias Agopian7922fa22009-05-18 15:08:03 -0700929 // Return immediately if there is nothing to do.
930 if ((bwr.write_size == 0) && (bwr.read_size == 0)) return NO_ERROR;
Andy McFadden457d51f2011-08-31 07:43:40 -0700931
Mathias Agopian7922fa22009-05-18 15:08:03 -0700932 bwr.write_consumed = 0;
933 bwr.read_consumed = 0;
934 status_t err;
935 do {
936 IF_LOG_COMMANDS() {
937 alog << "About to read/write, write size = " << mOut.dataSize() << endl;
938 }
Elliott Hughese5e70552015-08-12 15:27:47 -0700939#if defined(__ANDROID__)
Mathias Agopian7922fa22009-05-18 15:08:03 -0700940 if (ioctl(mProcess->mDriverFD, BINDER_WRITE_READ, &bwr) >= 0)
941 err = NO_ERROR;
942 else
943 err = -errno;
944#else
945 err = INVALID_OPERATION;
946#endif
Johannes Carlsson597a3c72011-02-17 14:06:53 +0100947 if (mProcess->mDriverFD <= 0) {
948 err = -EBADF;
949 }
Mathias Agopian7922fa22009-05-18 15:08:03 -0700950 IF_LOG_COMMANDS() {
951 alog << "Finished read/write, write size = " << mOut.dataSize() << endl;
952 }
953 } while (err == -EINTR);
Andy McFadden457d51f2011-08-31 07:43:40 -0700954
Mathias Agopian7922fa22009-05-18 15:08:03 -0700955 IF_LOG_COMMANDS() {
Colin Crossf0487982014-02-05 17:42:44 -0800956 alog << "Our err: " << (void*)(intptr_t)err << ", write consumed: "
Mathias Agopian7922fa22009-05-18 15:08:03 -0700957 << bwr.write_consumed << " (of " << mOut.dataSize()
Todd Poynor0646cb02013-06-25 19:12:18 -0700958 << "), read consumed: " << bwr.read_consumed << endl;
Mathias Agopian7922fa22009-05-18 15:08:03 -0700959 }
960
961 if (err >= NO_ERROR) {
962 if (bwr.write_consumed > 0) {
Arve Hjønnevåga5440702014-01-28 20:12:59 -0800963 if (bwr.write_consumed < mOut.dataSize())
Mathias Agopian7922fa22009-05-18 15:08:03 -0700964 mOut.remove(0, bwr.write_consumed);
Martijn Coenenb8253722018-05-23 15:33:22 +0200965 else {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700966 mOut.setDataSize(0);
Martijn Coenenb8253722018-05-23 15:33:22 +0200967 processPostWriteDerefs();
968 }
Mathias Agopian7922fa22009-05-18 15:08:03 -0700969 }
970 if (bwr.read_consumed > 0) {
971 mIn.setDataSize(bwr.read_consumed);
972 mIn.setDataPosition(0);
973 }
974 IF_LOG_COMMANDS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -0700975 alog << "Remaining data size: " << mOut.dataSize() << endl;
976 alog << "Received commands from driver: " << indent;
977 const void* cmds = mIn.data();
978 const void* end = mIn.data() + mIn.dataSize();
979 alog << HexDump(cmds, mIn.dataSize()) << endl;
980 while (cmds < end) cmds = printReturnCommand(alog, cmds);
981 alog << dedent;
982 }
983 return NO_ERROR;
984 }
Yifan Hongdde40f32017-01-12 14:22:45 -0800985
Mathias Agopian7922fa22009-05-18 15:08:03 -0700986 return err;
987}
988
989status_t IPCThreadState::writeTransactionData(int32_t cmd, uint32_t binderFlags,
990 int32_t handle, uint32_t code, const Parcel& data, status_t* statusBuffer)
991{
Martijn Coenenfd51ebb2016-07-05 17:00:39 +0200992 binder_transaction_data_sg tr_sg;
Christopher Ferris678434f2017-07-27 10:42:20 -0700993 /* Don't pass uninitialized stack data to a remote process */
994 tr_sg.transaction_data.target.ptr = 0;
995 tr_sg.transaction_data.target.handle = handle;
996 tr_sg.transaction_data.code = code;
997 tr_sg.transaction_data.flags = binderFlags;
998 tr_sg.transaction_data.cookie = 0;
999 tr_sg.transaction_data.sender_pid = 0;
1000 tr_sg.transaction_data.sender_euid = 0;
Yifan Hongdde40f32017-01-12 14:22:45 -08001001
Mathias Agopian7922fa22009-05-18 15:08:03 -07001002 const status_t err = data.errorCheck();
1003 if (err == NO_ERROR) {
Christopher Ferris678434f2017-07-27 10:42:20 -07001004 tr_sg.transaction_data.data_size = data.ipcDataSize();
1005 tr_sg.transaction_data.data.ptr.buffer = data.ipcData();
1006 tr_sg.transaction_data.offsets_size = data.ipcObjectsCount()*sizeof(binder_size_t);
1007 tr_sg.transaction_data.data.ptr.offsets = data.ipcObjects();
Martijn Coenenfd51ebb2016-07-05 17:00:39 +02001008 tr_sg.buffers_size = data.ipcBufferSize();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001009 } else if (statusBuffer) {
Christopher Ferris678434f2017-07-27 10:42:20 -07001010 tr_sg.transaction_data.flags |= TF_STATUS_CODE;
Mathias Agopian7922fa22009-05-18 15:08:03 -07001011 *statusBuffer = err;
Christopher Ferris678434f2017-07-27 10:42:20 -07001012 tr_sg.transaction_data.data_size = sizeof(status_t);
1013 tr_sg.transaction_data.data.ptr.buffer = reinterpret_cast<uintptr_t>(statusBuffer);
1014 tr_sg.transaction_data.offsets_size = 0;
1015 tr_sg.transaction_data.data.ptr.offsets = 0;
Martijn Coenenfd51ebb2016-07-05 17:00:39 +02001016 tr_sg.buffers_size = 0;
Mathias Agopian7922fa22009-05-18 15:08:03 -07001017 } else {
1018 return (mLastError = err);
1019 }
Yifan Hongdde40f32017-01-12 14:22:45 -08001020
Mathias Agopian7922fa22009-05-18 15:08:03 -07001021 mOut.writeInt32(cmd);
Martijn Coenenfd51ebb2016-07-05 17:00:39 +02001022 mOut.write(&tr_sg, sizeof(tr_sg));
Yifan Hongdde40f32017-01-12 14:22:45 -08001023
Mathias Agopian7922fa22009-05-18 15:08:03 -07001024 return NO_ERROR;
1025}
1026
Yifan Hongdde40f32017-01-12 14:22:45 -08001027void IPCThreadState::setTheContextObject(sp<BHwBinder> obj)
Mathias Agopian7922fa22009-05-18 15:08:03 -07001028{
Martijn Coenena660cbc2016-05-12 11:29:23 +02001029 mContextObject = obj;
Mathias Agopian7922fa22009-05-18 15:08:03 -07001030}
1031
Martijn Coenen420d4bb2017-10-24 11:43:55 +02001032bool IPCThreadState::isLooperThread()
1033{
1034 return mIsLooper;
1035}
1036
Tobias Lindskoga36d5762018-01-05 10:28:31 +01001037bool IPCThreadState::isOnlyBinderThread() {
1038 return (mIsLooper && mProcess->mMaxThreads <= 1) || mIsPollingThread;
1039}
1040
Steven Morelandd7bbfdb2018-05-01 16:30:46 -07001041void IPCThreadState::addPostCommandTask(const std::function<void(void)>& task) {
1042 mPostCommandTasks.push_back(task);
1043}
1044
Mathias Agopian7922fa22009-05-18 15:08:03 -07001045status_t IPCThreadState::executeCommand(int32_t cmd)
1046{
Yifan Hongdde40f32017-01-12 14:22:45 -08001047 BHwBinder* obj;
Mathias Agopian7922fa22009-05-18 15:08:03 -07001048 RefBase::weakref_type* refs;
1049 status_t result = NO_ERROR;
Bernhard Rosenkränzerb184ed02014-11-25 21:55:33 +01001050 switch ((uint32_t)cmd) {
Mathias Agopian7922fa22009-05-18 15:08:03 -07001051 case BR_ERROR:
1052 result = mIn.readInt32();
1053 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001054
Mathias Agopian7922fa22009-05-18 15:08:03 -07001055 case BR_OK:
1056 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001057
Mathias Agopian7922fa22009-05-18 15:08:03 -07001058 case BR_ACQUIRE:
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001059 refs = (RefBase::weakref_type*)mIn.readPointer();
Yifan Hongdde40f32017-01-12 14:22:45 -08001060 obj = (BHwBinder*)mIn.readPointer();
Steve Blockd0bfabc2012-01-09 18:35:44 +00001061 ALOG_ASSERT(refs->refBase() == obj,
Mathias Agopian7922fa22009-05-18 15:08:03 -07001062 "BR_ACQUIRE: object %p does not match cookie %p (expected %p)",
1063 refs, obj, refs->refBase());
1064 obj->incStrong(mProcess.get());
1065 IF_LOG_REMOTEREFS() {
1066 LOG_REMOTEREFS("BR_ACQUIRE from driver on %p", obj);
1067 obj->printRefs();
1068 }
1069 mOut.writeInt32(BC_ACQUIRE_DONE);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001070 mOut.writePointer((uintptr_t)refs);
1071 mOut.writePointer((uintptr_t)obj);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001072 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001073
Mathias Agopian7922fa22009-05-18 15:08:03 -07001074 case BR_RELEASE:
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001075 refs = (RefBase::weakref_type*)mIn.readPointer();
Yifan Hongdde40f32017-01-12 14:22:45 -08001076 obj = (BHwBinder*)mIn.readPointer();
Steve Blockd0bfabc2012-01-09 18:35:44 +00001077 ALOG_ASSERT(refs->refBase() == obj,
Mathias Agopian7922fa22009-05-18 15:08:03 -07001078 "BR_RELEASE: object %p does not match cookie %p (expected %p)",
1079 refs, obj, refs->refBase());
1080 IF_LOG_REMOTEREFS() {
1081 LOG_REMOTEREFS("BR_RELEASE from driver on %p", obj);
1082 obj->printRefs();
1083 }
1084 mPendingStrongDerefs.push(obj);
1085 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001086
Mathias Agopian7922fa22009-05-18 15:08:03 -07001087 case BR_INCREFS:
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001088 refs = (RefBase::weakref_type*)mIn.readPointer();
Yifan Hongdde40f32017-01-12 14:22:45 -08001089 obj = (BHwBinder*)mIn.readPointer();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001090 refs->incWeak(mProcess.get());
1091 mOut.writeInt32(BC_INCREFS_DONE);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001092 mOut.writePointer((uintptr_t)refs);
1093 mOut.writePointer((uintptr_t)obj);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001094 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001095
Mathias Agopian7922fa22009-05-18 15:08:03 -07001096 case BR_DECREFS:
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001097 refs = (RefBase::weakref_type*)mIn.readPointer();
Yifan Hongdde40f32017-01-12 14:22:45 -08001098 obj = (BHwBinder*)mIn.readPointer();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001099 // NOTE: This assertion is not valid, because the object may no
Yifan Hongdde40f32017-01-12 14:22:45 -08001100 // longer exist (thus the (BHwBinder*)cast above resulting in a different
Mathias Agopian7922fa22009-05-18 15:08:03 -07001101 // memory address).
Steve Blockd0bfabc2012-01-09 18:35:44 +00001102 //ALOG_ASSERT(refs->refBase() == obj,
Mathias Agopian7922fa22009-05-18 15:08:03 -07001103 // "BR_DECREFS: object %p does not match cookie %p (expected %p)",
1104 // refs, obj, refs->refBase());
1105 mPendingWeakDerefs.push(refs);
1106 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001107
Mathias Agopian7922fa22009-05-18 15:08:03 -07001108 case BR_ATTEMPT_ACQUIRE:
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001109 refs = (RefBase::weakref_type*)mIn.readPointer();
Yifan Hongdde40f32017-01-12 14:22:45 -08001110 obj = (BHwBinder*)mIn.readPointer();
1111
Mathias Agopian7922fa22009-05-18 15:08:03 -07001112 {
1113 const bool success = refs->attemptIncStrong(mProcess.get());
Steve Blockd0bfabc2012-01-09 18:35:44 +00001114 ALOG_ASSERT(success && refs->refBase() == obj,
Mathias Agopian7922fa22009-05-18 15:08:03 -07001115 "BR_ATTEMPT_ACQUIRE: object %p does not match cookie %p (expected %p)",
1116 refs, obj, refs->refBase());
Yifan Hongdde40f32017-01-12 14:22:45 -08001117
Mathias Agopian7922fa22009-05-18 15:08:03 -07001118 mOut.writeInt32(BC_ACQUIRE_RESULT);
1119 mOut.writeInt32((int32_t)success);
1120 }
1121 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001122
Mathias Agopian7922fa22009-05-18 15:08:03 -07001123 case BR_TRANSACTION:
1124 {
1125 binder_transaction_data tr;
1126 result = mIn.read(&tr, sizeof(tr));
Steve Blockd0bfabc2012-01-09 18:35:44 +00001127 ALOG_ASSERT(result == NO_ERROR,
Mathias Agopian7922fa22009-05-18 15:08:03 -07001128 "Not enough command data for brTRANSACTION");
1129 if (result != NO_ERROR) break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001130
Jayant Chowdhary985fc892018-10-01 22:54:05 +00001131 // Record the fact that we're in a hwbinder call
1132 mIPCThreadStateBase->pushCurrentState(
1133 IPCThreadStateBase::CallState::HWBINDER);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001134 Parcel buffer;
1135 buffer.ipcSetDataReference(
1136 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
1137 tr.data_size,
Arve Hjønnevåga5440702014-01-28 20:12:59 -08001138 reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
1139 tr.offsets_size/sizeof(binder_size_t), freeBuffer, this);
Yifan Hongdde40f32017-01-12 14:22:45 -08001140
Mathias Agopian7922fa22009-05-18 15:08:03 -07001141 const pid_t origPid = mCallingPid;
1142 const uid_t origUid = mCallingUid;
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001143 const int32_t origStrictModePolicy = mStrictModePolicy;
1144 const int32_t origTransactionBinderFlags = mLastTransactionBinderFlags;
1145
Mathias Agopian7922fa22009-05-18 15:08:03 -07001146 mCallingPid = tr.sender_pid;
1147 mCallingUid = tr.sender_euid;
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001148 mLastTransactionBinderFlags = tr.flags;
1149
Steve Block93cf8542012-01-04 20:05:49 +00001150 //ALOGI(">>>> TRANSACT from pid %d uid %d\n", mCallingPid, mCallingUid);
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001151
Mathias Agopian7922fa22009-05-18 15:08:03 -07001152 Parcel reply;
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001153 status_t error;
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001154 bool reply_sent = false;
Mathias Agopian7922fa22009-05-18 15:08:03 -07001155 IF_LOG_TRANSACTIONS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -07001156 alog << "BR_TRANSACTION thr " << (void*)pthread_self()
1157 << " / obj " << tr.target.ptr << " / code "
1158 << TypeCode(tr.code) << ": " << indent << buffer
1159 << dedent << endl
1160 << "Data addr = "
1161 << reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer)
1162 << ", offsets addr="
1163 << reinterpret_cast<const size_t*>(tr.data.ptr.offsets) << endl;
1164 }
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001165
1166 auto reply_callback = [&] (auto &replyParcel) {
1167 if (reply_sent) {
1168 // Reply was sent earlier, ignore it.
1169 ALOGE("Dropping binder reply, it was sent already.");
1170 return;
1171 }
1172 reply_sent = true;
1173 if ((tr.flags & TF_ONE_WAY) == 0) {
1174 replyParcel.setError(NO_ERROR);
1175 sendReply(replyParcel, 0);
1176 } else {
1177 ALOGE("Not sending reply in one-way transaction");
1178 }
1179 };
1180
Mathias Agopian7922fa22009-05-18 15:08:03 -07001181 if (tr.target.ptr) {
Dianne Hackborn839f7072016-03-21 10:36:54 -07001182 // We only have a weak reference on the target object, so we must first try to
1183 // safely acquire a strong reference before doing anything else with it.
1184 if (reinterpret_cast<RefBase::weakref_type*>(
1185 tr.target.ptr)->attemptIncStrong(this)) {
Yifan Hongdde40f32017-01-12 14:22:45 -08001186 error = reinterpret_cast<BHwBinder*>(tr.cookie)->transact(tr.code, buffer,
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001187 &reply, tr.flags, reply_callback);
Yifan Hongdde40f32017-01-12 14:22:45 -08001188 reinterpret_cast<BHwBinder*>(tr.cookie)->decStrong(this);
Dianne Hackborn839f7072016-03-21 10:36:54 -07001189 } else {
1190 error = UNKNOWN_TRANSACTION;
1191 }
Brad Fitzpatrick24f8bca2010-08-30 16:01:16 -07001192
Mathias Agopian7922fa22009-05-18 15:08:03 -07001193 } else {
Martijn Coenena660cbc2016-05-12 11:29:23 +02001194 error = mContextObject->transact(tr.code, buffer, &reply, tr.flags, reply_callback);
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001195 }
1196
Jayant Chowdhary985fc892018-10-01 22:54:05 +00001197 mIPCThreadStateBase->popCurrentState();
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001198 if ((tr.flags & TF_ONE_WAY) == 0) {
1199 if (!reply_sent) {
1200 // Should have been a reply but there wasn't, so there
1201 // must have been an error instead.
1202 reply.setError(error);
1203 sendReply(reply, 0);
1204 } else {
1205 if (error != NO_ERROR) {
1206 ALOGE("transact() returned error after sending reply.");
1207 } else {
1208 // Ok, reply sent and transact didn't return an error.
1209 }
1210 }
1211 } else {
1212 // One-way transaction, don't care about return value or reply.
Mathias Agopian7922fa22009-05-18 15:08:03 -07001213 }
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001214
Steve Block93cf8542012-01-04 20:05:49 +00001215 //ALOGI("<<<< TRANSACT from pid %d restore pid %d uid %d\n",
Mathias Agopian7922fa22009-05-18 15:08:03 -07001216 // mCallingPid, origPid, origUid);
Martijn Coenen79c2f4d2016-05-20 10:55:59 +02001217
Yifan Hongdde40f32017-01-12 14:22:45 -08001218
Mathias Agopian7922fa22009-05-18 15:08:03 -07001219 mCallingPid = origPid;
1220 mCallingUid = origUid;
Dianne Hackbornf99aec62014-09-30 11:30:03 -07001221 mStrictModePolicy = origStrictModePolicy;
1222 mLastTransactionBinderFlags = origTransactionBinderFlags;
Christopher Tate7c4dfec2010-03-18 17:55:03 -07001223
Mathias Agopian7922fa22009-05-18 15:08:03 -07001224 IF_LOG_TRANSACTIONS() {
Mathias Agopian7922fa22009-05-18 15:08:03 -07001225 alog << "BC_REPLY thr " << (void*)pthread_self() << " / obj "
1226 << tr.target.ptr << ": " << indent << reply << dedent << endl;
1227 }
Yifan Hongdde40f32017-01-12 14:22:45 -08001228
Mathias Agopian7922fa22009-05-18 15:08:03 -07001229 }
1230 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001231
Mathias Agopian7922fa22009-05-18 15:08:03 -07001232 case BR_DEAD_BINDER:
1233 {
Yifan Hong1e118d22017-01-12 14:42:28 -08001234 BpHwBinder *proxy = (BpHwBinder*)mIn.readPointer();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001235 proxy->sendObituary();
1236 mOut.writeInt32(BC_DEAD_BINDER_DONE);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001237 mOut.writePointer((uintptr_t)proxy);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001238 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001239
Mathias Agopian7922fa22009-05-18 15:08:03 -07001240 case BR_CLEAR_DEATH_NOTIFICATION_DONE:
1241 {
Yifan Hong1e118d22017-01-12 14:42:28 -08001242 BpHwBinder *proxy = (BpHwBinder*)mIn.readPointer();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001243 proxy->getWeakRefs()->decWeak(proxy);
1244 } break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001245
Mathias Agopian7922fa22009-05-18 15:08:03 -07001246 case BR_FINISHED:
1247 result = TIMED_OUT;
1248 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001249
Mathias Agopian7922fa22009-05-18 15:08:03 -07001250 case BR_NOOP:
1251 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001252
Mathias Agopian7922fa22009-05-18 15:08:03 -07001253 case BR_SPAWN_LOOPER:
1254 mProcess->spawnPooledThread(false);
1255 break;
Yifan Hongdde40f32017-01-12 14:22:45 -08001256
Mathias Agopian7922fa22009-05-18 15:08:03 -07001257 default:
1258 printf("*** BAD COMMAND %d received from Binder driver\n", cmd);
1259 result = UNKNOWN_ERROR;
1260 break;
1261 }
1262
1263 if (result != NO_ERROR) {
1264 mLastError = result;
1265 }
Yifan Hongdde40f32017-01-12 14:22:45 -08001266
Mathias Agopian7922fa22009-05-18 15:08:03 -07001267 return result;
1268}
1269
Jayant Chowdhary985fc892018-10-01 22:54:05 +00001270bool IPCThreadState::isServingCall() const
1271{
1272 return mIPCThreadStateBase->getCurrentBinderCallState() == IPCThreadStateBase::CallState::HWBINDER;
1273}
1274
Mathias Agopian7922fa22009-05-18 15:08:03 -07001275void IPCThreadState::threadDestructor(void *st)
1276{
Todd Poynor0646cb02013-06-25 19:12:18 -07001277 IPCThreadState* const self = static_cast<IPCThreadState*>(st);
1278 if (self) {
1279 self->flushCommands();
Elliott Hughese5e70552015-08-12 15:27:47 -07001280#if defined(__ANDROID__)
Johannes Carlsson597a3c72011-02-17 14:06:53 +01001281 if (self->mProcess->mDriverFD > 0) {
1282 ioctl(self->mProcess->mDriverFD, BINDER_THREAD_EXIT, 0);
1283 }
Mathias Agopian7922fa22009-05-18 15:08:03 -07001284#endif
Todd Poynor0646cb02013-06-25 19:12:18 -07001285 delete self;
1286 }
Mathias Agopian7922fa22009-05-18 15:08:03 -07001287}
1288
1289
Colin Crossf0487982014-02-05 17:42:44 -08001290void IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data,
1291 size_t /*dataSize*/,
1292 const binder_size_t* /*objects*/,
1293 size_t /*objectsSize*/, void* /*cookie*/)
Mathias Agopian7922fa22009-05-18 15:08:03 -07001294{
Steve Block93cf8542012-01-04 20:05:49 +00001295 //ALOGI("Freeing parcel %p", &parcel);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001296 IF_LOG_COMMANDS() {
1297 alog << "Writing BC_FREE_BUFFER for " << data << endl;
1298 }
Yi Kong55d41072018-07-23 14:55:39 -07001299 ALOG_ASSERT(data != nullptr, "Called with NULL data");
1300 if (parcel != nullptr) parcel->closeFileDescriptors();
Mathias Agopian7922fa22009-05-18 15:08:03 -07001301 IPCThreadState* state = self();
1302 state->mOut.writeInt32(BC_FREE_BUFFER);
Serban Constantinescu4ca5baf2013-11-05 16:53:55 +00001303 state->mOut.writePointer((uintptr_t)data);
Mathias Agopian7922fa22009-05-18 15:08:03 -07001304}
1305
Martijn Coenenf75a23d2016-08-01 11:55:17 +02001306}; // namespace hardware
Mathias Agopian7922fa22009-05-18 15:08:03 -07001307}; // namespace android