17922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian/*
27922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * Copyright (C) 2005 The Android Open Source Project
37922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian *
47922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * Licensed under the Apache License, Version 2.0 (the "License");
57922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * you may not use this file except in compliance with the License.
67922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * You may obtain a copy of the License at
77922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian *
87922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian *      http://www.apache.org/licenses/LICENSE-2.0
97922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian *
107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * Unless required by applicable law or agreed to in writing, software
117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * distributed under the License is distributed on an "AS IS" BASIS,
127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * See the License for the specific language governing permissions and
147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian * limitations under the License.
157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian */
167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
17c4dd210df92f8d58adae5e27631be4d92cba0c43Steven Moreland#define LOG_TAG "hw-IPCThreadState"
182b17f147508401f8e8cdf59f7a329cb677bd7eadJason Parks
194080edcfb5810a4a1817c03740f5f1bb19815ae1Martijn Coenen#include <hwbinder/IPCThreadState.h>
207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
214080edcfb5810a4a1817c03740f5f1bb19815ae1Martijn Coenen#include <hwbinder/Binder.h>
221e118d2b86540f7a7d840ec1510337da49f1446cYifan Hong#include <hwbinder/BpHwBinder.h>
234080edcfb5810a4a1817c03740f5f1bb19815ae1Martijn Coenen#include <hwbinder/TextOutput.h>
240e72fd55c5369bfdb3e61b11f720c5f118fa3031Chia-I Wu#include <hwbinder/binder_kernel.h>
254ea13dcd270953215f51345e83708c16963d332fMathias Agopian
267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <utils/Log.h>
27b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross#include <utils/SystemClock.h>
287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <utils/threads.h>
297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <private/binder/binder_module.h>
31e01f4f2b38beb5799dece8742eef5d70d131dbd3Martijn Coenen#include <hwbinder/Static.h>
327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <errno.h>
34b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross#include <inttypes.h>
357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <pthread.h>
367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <sched.h>
37bbef2baee419a27bc8e8c40e80e296b145e2c9abYabin Cui#include <signal.h>
38bbef2baee419a27bc8e8c40e80e296b145e2c9abYabin Cui#include <stdio.h>
39bbef2baee419a27bc8e8c40e80e296b145e2c9abYabin Cui#include <sys/ioctl.h>
407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#include <sys/resource.h>
41bbef2baee419a27bc8e8c40e80e296b145e2c9abYabin Cui#include <unistd.h>
427922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
437922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#if LOG_NDEBUG
447922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
457922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#define IF_LOG_TRANSACTIONS() if (false)
467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#define IF_LOG_COMMANDS() if (false)
47dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong#define LOG_REMOTEREFS(...)
487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#define IF_LOG_REMOTEREFS() if (false)
49dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong#define LOG_THREADPOOL(...)
50dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong#define LOG_ONEWAY(...)
517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#else
537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
545854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define IF_LOG_TRANSACTIONS() IF_ALOG(LOG_VERBOSE, "transact")
555854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define IF_LOG_COMMANDS() IF_ALOG(LOG_VERBOSE, "ipc")
565854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define LOG_REMOTEREFS(...) ALOG(LOG_DEBUG, "remoterefs", __VA_ARGS__)
575854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define IF_LOG_REMOTEREFS() IF_ALOG(LOG_DEBUG, "remoterefs")
585854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define LOG_THREADPOOL(...) ALOG(LOG_DEBUG, "threadpool", __VA_ARGS__)
595854b917f0d7b18a74786f652a981f241cc906f5Steve Block#define LOG_ONEWAY(...) ALOG(LOG_DEBUG, "ipc", __VA_ARGS__)
607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#endif
627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian// ---------------------------------------------------------------------------
647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopiannamespace android {
66f75a23d54cc9e5f7b6b976e65b6ec346178f306dMartijn Coenennamespace hardware {
677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6830dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh// Static const and functions will be optimized out if not used,
6930dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh// when LOG_NDEBUG and references in IF_LOG_COMMANDS() are optimized out.
707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const char *kReturnStrings[] = {
71457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    "BR_ERROR",
727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_OK",
737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_TRANSACTION",
747922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_REPLY",
757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_ACQUIRE_RESULT",
767922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_DEAD_REPLY",
777922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_TRANSACTION_COMPLETE",
787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_INCREFS",
797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_ACQUIRE",
807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_RELEASE",
817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_DECREFS",
827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_ATTEMPT_ACQUIRE",
837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_NOOP",
847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_SPAWN_LOOPER",
857922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_FINISHED",
867922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BR_DEAD_BINDER",
87457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    "BR_CLEAR_DEATH_NOTIFICATION_DONE",
88457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    "BR_FAILED_REPLY"
897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian};
907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
917922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const char *kCommandStrings[] = {
927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_TRANSACTION",
937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_REPLY",
947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_ACQUIRE_RESULT",
957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_FREE_BUFFER",
967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_INCREFS",
977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_ACQUIRE",
987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_RELEASE",
997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_DECREFS",
1007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_INCREFS_DONE",
1017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_ACQUIRE_DONE",
1027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_ATTEMPT_ACQUIRE",
1037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_REGISTER_LOOPER",
1047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_ENTER_LOOPER",
1057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_EXIT_LOOPER",
1067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_REQUEST_DEATH_NOTIFICATION",
1077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_CLEAR_DEATH_NOTIFICATION",
1087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    "BC_DEAD_BINDER_DONE"
1097922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian};
1107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const char* getReturnString(size_t idx)
1127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
1137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (idx < sizeof(kReturnStrings) / sizeof(kReturnStrings[0]))
1147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return kReturnStrings[idx];
1157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    else
1167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return "unknown";
1177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
1187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1197922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const void* printBinderTransactionData(TextOutput& out, const void* data)
1207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
1217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const binder_transaction_data* btd =
1227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        (const binder_transaction_data*)data;
123457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    if (btd->target.handle < 1024) {
124457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        /* want to print descriptors in decimal; guess based on value */
125457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        out << "target.desc=" << btd->target.handle;
126457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    } else {
127457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        out << "target.ptr=" << btd->target.ptr;
128457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    }
129457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    out << " (cookie " << btd->cookie << ")" << endl
13030dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh        << "code=" << TypeCode(btd->code) << ", flags=" << (void*)(long)btd->flags << endl
1317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        << "data=" << btd->data.ptr.buffer << " (" << (void*)btd->data_size
1327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        << " bytes)" << endl
1337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        << "offsets=" << btd->data.ptr.offsets << " (" << (void*)btd->offsets_size
134457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        << " bytes)";
1357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return btd+1;
1367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
1377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const void* printReturnCommand(TextOutput& out, const void* _cmd)
1397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
140457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    static const size_t N = sizeof(kReturnStrings)/sizeof(kReturnStrings[0]);
1417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const int32_t* cmd = (const int32_t*)_cmd;
142b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer    uint32_t code = (uint32_t)*cmd++;
143457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    size_t cmdIndex = code & 0xff;
144b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer    if (code == BR_ERROR) {
14530dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh        out << "BR_ERROR: " << (void*)(long)(*cmd++) << endl;
1467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return cmd;
147457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    } else if (cmdIndex >= N) {
1487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        out << "Unknown reply: " << code << endl;
1497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return cmd;
1507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
151457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    out << kReturnStrings[cmdIndex];
152dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
1537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    switch (code) {
1547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_TRANSACTION:
1557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_REPLY: {
1567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << ": " << indent;
1577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            cmd = (const int32_t *)printBinderTransactionData(out, cmd);
1587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << dedent;
1597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
160dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
1617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_ACQUIRE_RESULT: {
1627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t res = *cmd++;
1637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)");
1647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
165dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
1667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_INCREFS:
1677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_ACQUIRE:
1687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_RELEASE:
1697922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_DECREFS: {
1707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t b = *cmd++;
1717922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
17230dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c << ")";
1737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
174dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
1757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_ATTEMPT_ACQUIRE: {
1767922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t p = *cmd++;
1777922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t b = *cmd++;
1787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
17930dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c
1807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                << "), pri=" << p;
1817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
1827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_DEAD_BINDER:
1847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_CLEAR_DEATH_NOTIFICATION_DONE: {
1857922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
18630dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": death cookie " << (void*)(long)c;
1877922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
188457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
189457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        default:
190457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            // no details to show for: BR_OK, BR_DEAD_REPLY,
191457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            // BR_TRANSACTION_COMPLETE, BR_FINISHED
192457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            break;
1937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
194dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
1957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    out << endl;
1967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return cmd;
1977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
1987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic const void* printCommand(TextOutput& out, const void* _cmd)
2007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
201457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    static const size_t N = sizeof(kCommandStrings)/sizeof(kCommandStrings[0]);
2027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const int32_t* cmd = (const int32_t*)_cmd;
203b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer    uint32_t code = (uint32_t)*cmd++;
204457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    size_t cmdIndex = code & 0xff;
205457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
206457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    if (cmdIndex >= N) {
2077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        out << "Unknown command: " << code << endl;
2087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return cmd;
2097922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
210457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    out << kCommandStrings[cmdIndex];
211457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
2127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    switch (code) {
2137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_TRANSACTION:
2147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_REPLY: {
2157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << ": " << indent;
2167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            cmd = (const int32_t *)printBinderTransactionData(out, cmd);
2177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << dedent;
2187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
219dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_ACQUIRE_RESULT: {
2217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t res = *cmd++;
2227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)");
2237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
224dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_FREE_BUFFER: {
2267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t buf = *cmd++;
22730dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": buffer=" << (void*)(long)buf;
2287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
229dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_INCREFS:
2317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_ACQUIRE:
2327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_RELEASE:
2337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_DECREFS: {
2347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t d = *cmd++;
235457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            out << ": desc=" << d;
2367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
237dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_INCREFS_DONE:
2397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_ACQUIRE_DONE: {
2407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t b = *cmd++;
2417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
24230dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": target=" << (void*)(long)b << " (cookie " << (void*)(long)c << ")";
2437922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
244dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2457922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_ATTEMPT_ACQUIRE: {
2467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t p = *cmd++;
2477922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t d = *cmd++;
248457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            out << ": desc=" << d << ", pri=" << p;
2497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
250dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_REQUEST_DEATH_NOTIFICATION:
2527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_CLEAR_DEATH_NOTIFICATION: {
2537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t h = *cmd++;
2547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
25530dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": handle=" << h << " (death cookie " << (void*)(long)c << ")";
2567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
2577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
2587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BC_DEAD_BINDER_DONE: {
2597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const int32_t c = *cmd++;
26030dcad775deba8134cbbcb93a9b15412f9b1d2a0Chih-Hung Hsieh            out << ": death cookie " << (void*)(long)c;
2617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
262457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
263457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden        default:
264457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            // no details to show for: BC_REGISTER_LOOPER, BC_ENTER_LOOPER,
265457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            // BC_EXIT_LOOPER
266457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden            break;
2677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
268dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2697922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    out << endl;
2707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return cmd;
2717922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
2727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
2737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic pthread_mutex_t gTLSMutex = PTHREAD_MUTEX_INITIALIZER;
2747922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic bool gHaveTLS = false;
2757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic pthread_key_t gTLS = 0;
2767922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatic bool gShutdown = false;
2775f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackbornstatic bool gDisableBackgroundScheduling = false;
2787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
2797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias AgopianIPCThreadState* IPCThreadState::self()
2807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
2817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (gHaveTLS) {
2827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianrestart:
2837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        const pthread_key_t k = gTLS;
2847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k);
2857922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (st) return st;
2867922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return new IPCThreadState;
2877922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
288dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2891d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe    if (gShutdown) {
2901d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe        ALOGW("Calling IPCThreadState::self() during shutdown is dangerous, expect a crash.\n");
2911d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe        return NULL;
2921d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe    }
293dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
2947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    pthread_mutex_lock(&gTLSMutex);
2957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (!gHaveTLS) {
2961d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe        int key_create_value = pthread_key_create(&gTLS, threadDestructor);
2971d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe        if (key_create_value != 0) {
2987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            pthread_mutex_unlock(&gTLSMutex);
2991d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe            ALOGW("IPCThreadState::self() unable to create TLS key, expect a crash: %s\n",
3001d5dc2bf97110aa3a00236afc64018dfe79b97d8Andreas Gampe                    strerror(key_create_value));
3017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            return NULL;
3027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
3037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        gHaveTLS = true;
3047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
3057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    pthread_mutex_unlock(&gTLSMutex);
3067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    goto restart;
3077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
3097794994fc8947b65730108aa4700b109c268bb6dBrad FitzpatrickIPCThreadState* IPCThreadState::selfOrNull()
3107794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick{
3117794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick    if (gHaveTLS) {
3127794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick        const pthread_key_t k = gTLS;
3137794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick        IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k);
3147794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick        return st;
3157794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick    }
3167794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick    return NULL;
3177794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick}
3187794994fc8947b65730108aa4700b109c268bb6dBrad Fitzpatrick
3197922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::shutdown()
3207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    gShutdown = true;
322dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
3237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (gHaveTLS) {
3247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // XXX Need to wait for all thread pool threads to exit!
3257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IPCThreadState* st = (IPCThreadState*)pthread_getspecific(gTLS);
3267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (st) {
3277922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            delete st;
3287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            pthread_setspecific(gTLS, NULL);
3297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
3308e8a025a6587a97e3ed048b47a02575551f4db43zhongjie        pthread_key_delete(gTLS);
3317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        gHaveTLS = false;
3327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
3337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
3355f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackbornvoid IPCThreadState::disableBackgroundScheduling(bool disable)
3365f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackborn{
3375f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackborn    gDisableBackgroundScheduling = disable;
3385f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackborn}
3395f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackborn
3407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopiansp<ProcessState> IPCThreadState::process()
3417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3427922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return mProcess;
3437922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3447922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
3457922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::clearLastError()
3467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3477922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const status_t err = mLastError;
3487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mLastError = NO_ERROR;
3497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return err;
3507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
352e8da8a4d96938fbe2db67928f176ab11d341ac31Dan Stozapid_t IPCThreadState::getCallingPid() const
3537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return mCallingPid;
3557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
357e8da8a4d96938fbe2db67928f176ab11d341ac31Dan Stozauid_t IPCThreadState::getCallingUid() const
3587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return mCallingUid;
3607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
3627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianint64_t IPCThreadState::clearCallingIdentity()
3637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    int64_t token = ((int64_t)mCallingUid<<32) | mCallingPid;
3657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    clearCaller();
3667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return token;
3677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
36994c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrickvoid IPCThreadState::setStrictModePolicy(int32_t policy)
37094c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick{
37194c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick    mStrictModePolicy = policy;
37294c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick}
37394c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick
3743f4ef59401d7c2115c273ab1e76c221da22cf8d0Brad Fitzpatrickint32_t IPCThreadState::getStrictModePolicy() const
3753f4ef59401d7c2115c273ab1e76c221da22cf8d0Brad Fitzpatrick{
37694c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick    return mStrictModePolicy;
37794c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick}
37894c3634ac573531efe9a5abbc122a35c201567adBrad Fitzpatrick
37924f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrickvoid IPCThreadState::setLastTransactionBinderFlags(int32_t flags)
38024f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick{
38124f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick    mLastTransactionBinderFlags = flags;
38224f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick}
38324f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick
38424f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrickint32_t IPCThreadState::getLastTransactionBinderFlags() const
38524f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick{
38624f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick    return mLastTransactionBinderFlags;
38724f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick}
38824f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick
3897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::restoreCallingIdentity(int64_t token)
3907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
3917922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mCallingUid = (int)(token>>32);
3927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mCallingPid = (int)token;
3937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
3947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
3957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::clearCaller()
3967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
397b4f35d0238103bd22c1a2cf1b6a31f2fba21fc3eMarco Nelissen    mCallingPid = getpid();
398b4f35d0238103bd22c1a2cf1b6a31f2fba21fc3eMarco Nelissen    mCallingUid = getuid();
3997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
4007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
4017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::flushCommands()
4027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
4037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (mProcess->mDriverFD <= 0)
4047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return;
4057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    talkWithDriver(false);
406b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    // The flush could have caused post-write refcount decrements to have
407b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    // been executed, which in turn could result in BC_RELEASE/BC_DECREFS
408b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    // being queued in mOut. So flush again, if we need to.
409b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    if (mOut.dataSize() > 0) {
410b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        talkWithDriver(false);
411b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    }
412b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    if (mOut.dataSize() > 0) {
413b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        ALOGW("mOut.dataSize() > 0 after flushCommands()");
414b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    }
4157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
4167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
4172e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwalevoid IPCThreadState::blockUntilThreadAvailable()
4182e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale{
4192e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale    pthread_mutex_lock(&mProcess->mThreadCountLock);
4202e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale    while (mProcess->mExecutingThreadsCount >= mProcess->mMaxThreads) {
421319900a48d6dfdb230d5eba0658ef92682145339Wale Ogunwale        ALOGW("Waiting for thread to be free. mExecutingThreadsCount=%lu mMaxThreads=%lu\n",
422319900a48d6dfdb230d5eba0658ef92682145339Wale Ogunwale                static_cast<unsigned long>(mProcess->mExecutingThreadsCount),
423319900a48d6dfdb230d5eba0658ef92682145339Wale Ogunwale                static_cast<unsigned long>(mProcess->mMaxThreads));
4242e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_cond_wait(&mProcess->mThreadCountDecrement, &mProcess->mThreadCountLock);
4252e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale    }
4262e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale    pthread_mutex_unlock(&mProcess->mThreadCountLock);
4272e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale}
4282e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale
4290646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynorstatus_t IPCThreadState::getAndExecuteCommand()
4300646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor{
4310646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    status_t result;
4320646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    int32_t cmd;
4330646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
4340646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    result = talkWithDriver();
4350646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    if (result >= NO_ERROR) {
4360646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        size_t IN = mIn.dataAvail();
4370646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        if (IN < sizeof(int32_t)) return result;
4380646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        cmd = mIn.readInt32();
4390646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        IF_LOG_COMMANDS() {
4400646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor            alog << "Processing top-level Command: "
4410646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                 << getReturnString(cmd) << endl;
4420646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        }
4430646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
4442e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_mutex_lock(&mProcess->mThreadCountLock);
4452e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        mProcess->mExecutingThreadsCount++;
446b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross        if (mProcess->mExecutingThreadsCount >= mProcess->mMaxThreads &&
4470ce07ce06005048eeef327af14b8958878e1aad7Martijn Coenen            mProcess->mMaxThreads > 1 && mProcess->mStarvationStartTimeMs == 0) {
448b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross            mProcess->mStarvationStartTimeMs = uptimeMillis();
449b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross        }
4502e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_mutex_unlock(&mProcess->mThreadCountLock);
4512e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale
4520646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        result = executeCommand(cmd);
4530646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
4542e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_mutex_lock(&mProcess->mThreadCountLock);
4552e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        mProcess->mExecutingThreadsCount--;
456df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang        if (mProcess->mExecutingThreadsCount < mProcess->mMaxThreads &&
4570ce07ce06005048eeef327af14b8958878e1aad7Martijn Coenen            mProcess->mStarvationStartTimeMs != 0) {
458b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross            int64_t starvationTimeMs = uptimeMillis() - mProcess->mStarvationStartTimeMs;
459b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross            if (starvationTimeMs > 100) {
460df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang                // If there is only a single-threaded client, nobody would be blocked
461df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang                // on this, and it's not really starvation. (see b/37647467)
462df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang                ALOGW("All binder threads in pool (%zu threads) busy for %" PRId64 " ms%s",
463df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang                      mProcess->mMaxThreads, starvationTimeMs,
464df7f40d43c85b342b9bed680a43c2acdd631aefbWei Wang                      mProcess->mMaxThreads > 1 ? "" : " (may be a false alarm)");
465b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross            }
466b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross            mProcess->mStarvationStartTimeMs = 0;
467b1dc654b9dbf8640605629a64b646ef1577c0db9Colin Cross        }
4682e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_cond_broadcast(&mProcess->mThreadCountDecrement);
4692e604f066e712d99b5cd8ba4115f7ed2578d4a5dWale Ogunwale        pthread_mutex_unlock(&mProcess->mThreadCountLock);
4700646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    }
4710646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
4720646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    return result;
4730646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor}
4740646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
4750646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor// When we've cleared the incoming command queue, process any pending derefs
4760646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynorvoid IPCThreadState::processPendingDerefs()
4770646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor{
4780646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    if (mIn.dataPosition() >= mIn.dataSize()) {
479c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen        /*
480c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * The decWeak()/decStrong() calls may cause a destructor to run,
481c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * which in turn could have initiated an outgoing transaction,
482c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * which in turn could cause us to add to the pending refs
483c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * vectors; so instead of simply iterating, loop until they're empty.
484c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         *
485c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * We do this in an outer loop, because calling decStrong()
486c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * may result in something being added to mPendingWeakDerefs,
487c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * which could be delayed until the next incoming command
488c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         * from the driver if we don't process it now.
489c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen         */
490c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen        while (mPendingWeakDerefs.size() > 0 || mPendingStrongDerefs.size() > 0) {
491c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen            while (mPendingWeakDerefs.size() > 0) {
492c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                RefBase::weakref_type* refs = mPendingWeakDerefs[0];
493c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                mPendingWeakDerefs.removeAt(0);
4940646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                refs->decWeak(mProcess.get());
4950646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor            }
4960646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
497c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen            if (mPendingStrongDerefs.size() > 0) {
498c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                // We don't use while() here because we don't want to re-order
499c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                // strong and weak decs at all; if this decStrong() causes both a
500c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                // decWeak() and a decStrong() to be queued, we want to process
501c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                // the decWeak() first.
502c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                BHwBinder* obj = mPendingStrongDerefs[0];
503c9f105ba3a7355b833a3c01b3a0cfb641fc07979Martijn Coenen                mPendingStrongDerefs.removeAt(0);
5040646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                obj->decStrong(mProcess.get());
5050646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor            }
5060646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        }
5070646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    }
5080646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor}
5090646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
510b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenenvoid IPCThreadState::processPostWriteDerefs()
511b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen{
512b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    /*
513b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen     * libhwbinder has a flushCommands() in the BpHwBinder destructor,
514b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen     * which makes this function (potentially) reentrant.
515b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen     * New entries shouldn't be added though, so just iterating until empty
516b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen     * should be safe.
517b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen     */
518b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    while (mPostWriteWeakDerefs.size() > 0) {
519b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        RefBase::weakref_type* refs = mPostWriteWeakDerefs[0];
520b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        mPostWriteWeakDerefs.removeAt(0);
521b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        refs->decWeak(mProcess.get());
522b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    }
523b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen
524b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    while (mPostWriteStrongDerefs.size() > 0) {
525b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        RefBase* obj = mPostWriteStrongDerefs[0];
526b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        mPostWriteStrongDerefs.removeAt(0);
527b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen        obj->decStrong(mProcess.get());
528b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    }
529b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen}
530b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen
5317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::joinThreadPool(bool isMain)
5327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
5337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    LOG_THREADPOOL("**** THREAD %p (PID %d) IS JOINING THE THREAD POOL\n", (void*)pthread_self(), getpid());
5347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
5357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(isMain ? BC_ENTER_LOOPER : BC_REGISTER_LOOPER);
536dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
5377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t result;
538420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen    mIsLooper = true;
5397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    do {
5400646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        processPendingDerefs();
5417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // now get the next command to be processed, waiting if necessary
5420646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        result = getAndExecuteCommand();
5432b17f147508401f8e8cdf59f7a329cb677bd7eadJason Parks
5440646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        if (result < NO_ERROR && result != TIMED_OUT && result != -ECONNREFUSED && result != -EBADF) {
5450646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor            ALOGE("getAndExecuteCommand(fd=%d) returned unexpected error %d, aborting",
546ee711ec34a64cf71e5f3e9c1494a988fd9002936Jeff Tinker                  mProcess->mDriverFD, result);
547ee711ec34a64cf71e5f3e9c1494a988fd9002936Jeff Tinker            abort();
5487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
549dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
5507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // Let this thread exit the thread pool if it is no longer
5517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // needed and it is not the main process thread.
5527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if(result == TIMED_OUT && !isMain) {
5537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            break;
5547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
5557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } while (result != -ECONNREFUSED && result != -EBADF);
5567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
5578a2e8ac7b2a44b6f37e209fa186a06326e82661eWei Wang    LOG_THREADPOOL("**** THREAD %p (PID %d) IS LEAVING THE THREAD POOL err=%d\n",
5588a2e8ac7b2a44b6f37e209fa186a06326e82661eWei Wang        (void*)pthread_self(), getpid(), result);
559dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
5607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_EXIT_LOOPER);
561420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen    mIsLooper = false;
5627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    talkWithDriver(false);
5637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
5647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
5650646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynorint IPCThreadState::setupPolling(int* fd)
5660646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor{
5670646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    if (mProcess->mDriverFD <= 0) {
5680646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        return -EBADF;
5690646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    }
5700646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
57180b88ab21170f7fde645212a9f6b6d7e28a40de4Martijn Coenen    // Tells the kernel to not spawn any additional binder threads,
57280b88ab21170f7fde645212a9f6b6d7e28a40de4Martijn Coenen    // as that won't work with polling. Also, the caller is responsible
57380b88ab21170f7fde645212a9f6b6d7e28a40de4Martijn Coenen    // for subsequently calling handlePolledCommands()
57480b88ab21170f7fde645212a9f6b6d7e28a40de4Martijn Coenen    mProcess->setThreadPoolConfiguration(1, true /* callerWillJoin */);
575a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog    mIsPollingThread = true;
57680b88ab21170f7fde645212a9f6b6d7e28a40de4Martijn Coenen
5770646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    mOut.writeInt32(BC_ENTER_LOOPER);
5780646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    *fd = mProcess->mDriverFD;
5790646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    return 0;
5800646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor}
5810646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
5820646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynorstatus_t IPCThreadState::handlePolledCommands()
5830646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor{
5840646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    status_t result;
5850646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
5860646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    do {
5870646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        result = getAndExecuteCommand();
5880646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    } while (mIn.dataPosition() < mIn.dataSize());
5890646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
5900646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    processPendingDerefs();
5910646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    flushCommands();
5920646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor    return result;
5930646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor}
5940646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor
595f04879896beb41f2455017ace482283bc2ef321cColin Crossvoid IPCThreadState::stopProcess(bool /*immediate*/)
5967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
59793cf854f5e563ba575691b4b639365fe6c517193Steve Block    //ALOGI("**** STOPPING PROCESS");
5987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    flushCommands();
5997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    int fd = mProcess->mDriverFD;
6007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mProcess->mDriverFD = -1;
6017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    close(fd);
6027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    //kill(getpid(), SIGKILL);
6037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::transact(int32_t handle,
6067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                                  uint32_t code, const Parcel& data,
6077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                                  Parcel* reply, uint32_t flags)
6087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
609ce45b8956abc22667c4b59621c5a983d1e19f6d7Ganesh Mahendran    status_t err;
6107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    flags |= TF_ACCEPT_FDS;
6127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    IF_LOG_TRANSACTIONS() {
6147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        alog << "BC_TRANSACTION thr " << (void*)pthread_self() << " / hand "
6157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            << handle << " / code " << TypeCode(code) << ": "
6167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            << indent << data << dedent << endl;
6177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
618dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
619ce45b8956abc22667c4b59621c5a983d1e19f6d7Ganesh Mahendran    LOG_ONEWAY(">>>> SEND from pid %d uid %d %s", getpid(), getuid(),
620ce45b8956abc22667c4b59621c5a983d1e19f6d7Ganesh Mahendran        (flags & TF_ONE_WAY) == 0 ? "READ REPLY" : "ONE WAY");
621ce45b8956abc22667c4b59621c5a983d1e19f6d7Ganesh Mahendran    err = writeTransactionData(BC_TRANSACTION_SG, flags, handle, code, data, NULL);
622dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
6237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (err != NO_ERROR) {
6247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (reply) reply->setError(err);
6257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return (mLastError = err);
6267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
627dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
6287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if ((flags & TF_ONE_WAY) == 0) {
6299887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        #if 0
6309887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        if (code == 4) { // relayout
63193cf854f5e563ba575691b4b639365fe6c517193Steve Block            ALOGI(">>>>>> CALLING transaction 4");
6329887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        } else {
63393cf854f5e563ba575691b4b639365fe6c517193Steve Block            ALOGI(">>>>>> CALLING transaction %d", code);
6349887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        }
6359887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        #endif
6367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (reply) {
6377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = waitForResponse(reply);
6387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } else {
6397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            Parcel fakeReply;
6407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = waitForResponse(&fakeReply);
6417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
6429887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        #if 0
6439887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        if (code == 4) { // relayout
64493cf854f5e563ba575691b4b639365fe6c517193Steve Block            ALOGI("<<<<<< RETURNING transaction 4");
6459887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        } else {
64693cf854f5e563ba575691b4b639365fe6c517193Steve Block            ALOGI("<<<<<< RETURNING transaction %d", code);
6479887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        }
6489887826b424612da22b61bc2b73adc88a4af9c7cDianne Hackborn        #endif
649dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
6507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_TRANSACTIONS() {
6517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "BR_REPLY thr " << (void*)pthread_self() << " / hand "
6527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                << handle << ": ";
6537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if (reply) alog << indent << *reply << dedent << endl;
6547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            else alog << "(none requested)" << endl;
6557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
6567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } else {
6577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        err = waitForResponse(NULL, NULL);
6587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
659dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
6607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return err;
6617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
663b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenenvoid IPCThreadState::incStrongHandle(int32_t handle, BpHwBinder *proxy)
6647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
6657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    LOG_REMOTEREFS("IPCThreadState::incStrongHandle(%d)\n", handle);
6667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_ACQUIRE);
6677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(handle);
668b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    // Create a temp reference until the driver has handled this command.
669b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    proxy->incStrong(mProcess.get());
670b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    mPostWriteStrongDerefs.push(proxy);
6717922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::decStrongHandle(int32_t handle)
6747922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
6757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    LOG_REMOTEREFS("IPCThreadState::decStrongHandle(%d)\n", handle);
6767922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_RELEASE);
6777922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(handle);
6787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
680b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenenvoid IPCThreadState::incWeakHandle(int32_t handle, BpHwBinder *proxy)
6817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
6827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    LOG_REMOTEREFS("IPCThreadState::incWeakHandle(%d)\n", handle);
6837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_INCREFS);
6847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(handle);
685b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    // Create a temp reference until the driver has handled this command.
686b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    proxy->getWeakRefs()->incWeak(mProcess.get());
687b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen    mPostWriteWeakDerefs.push(proxy->getWeakRefs());
6887922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::decWeakHandle(int32_t handle)
6917922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
6927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    LOG_REMOTEREFS("IPCThreadState::decWeakHandle(%d)\n", handle);
6937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_DECREFS);
6947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(handle);
6957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
6967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
6977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::attemptIncStrongHandle(int32_t handle)
6987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
699304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg#if HAS_BC_ATTEMPT_ACQUIRE
700457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden    LOG_REMOTEREFS("IPCThreadState::attemptIncStrongHandle(%d)\n", handle);
7017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_ATTEMPT_ACQUIRE);
7027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(0); // xxx was thread priority
7037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(handle);
7047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t result = UNKNOWN_ERROR;
705dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    waitForResponse(NULL, &result);
707dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#if LOG_REFCOUNTS
7097922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    printf("IPCThreadState::attemptIncStrongHandle(%ld) = %s\n",
7107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        handle, result == NO_ERROR ? "SUCCESS" : "FAILURE");
7117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#endif
712dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return result;
714304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg#else
715304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg    (void)handle;
716304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg    ALOGE("%s(%d): Not supported\n", __func__, handle);
717304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg    return INVALID_OPERATION;
718304dcaedb7aabc7d070329e641fc4a6a3bac2918Arve Hjønnevåg#endif
7197922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::expungeHandle(int32_t handle, IBinder* binder)
7227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
7237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#if LOG_REFCOUNTS
7247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    printf("IPCThreadState::expungeHandle(%ld)\n", handle);
7257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#endif
7266b65ac3d560d8d4c3289d56ad4b8e99e13805558Yunlian Jiang    self()->mProcess->expungeHandle(handle, binder);  // NOLINT
7277922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7291e118d2b86540f7a7d840ec1510337da49f1446cYifan Hongstatus_t IPCThreadState::requestDeathNotification(int32_t handle, BpHwBinder* proxy)
7307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
7317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_REQUEST_DEATH_NOTIFICATION);
7327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32((int32_t)handle);
7334ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu    mOut.writePointer((uintptr_t)proxy);
7347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return NO_ERROR;
7357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7371e118d2b86540f7a7d840ec1510337da49f1446cYifan Hongstatus_t IPCThreadState::clearDeathNotification(int32_t handle, BpHwBinder* proxy)
7387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
7397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(BC_CLEAR_DEATH_NOTIFICATION);
7407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32((int32_t)handle);
7414ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu    mOut.writePointer((uintptr_t)proxy);
7427922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return NO_ERROR;
7437922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7447922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7457922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias AgopianIPCThreadState::IPCThreadState()
74624f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick    : mProcess(ProcessState::self()),
74707cf48a1aaa0601c837024d159599ed9de19f5a9Elliott Hughes      mMyThreadId(gettid()),
74824f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick      mStrictModePolicy(0),
7499bd3d3bdc14465cdf86c5c28f9def6c43202a239Martijn Coenen      mLastTransactionBinderFlags(0),
750a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog      mIsLooper(false),
751a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog      mIsPollingThread(false) {
7527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    pthread_setspecific(gTLS, this);
7535f4d7e81777db67004bdd7836a133607c37ae936Dianne Hackborn    clearCaller();
7547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mIn.setDataCapacity(256);
7557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.setDataCapacity(256);
75629dbdcf1087e2d60c5898233aff0bb444147c4ffChih-Hung Hsieh
75729dbdcf1087e2d60c5898233aff0bb444147c4ffChih-Hung Hsieh    // TODO(b/67742352): remove this variable from the class
75829dbdcf1087e2d60c5898233aff0bb444147c4ffChih-Hung Hsieh    (void)mMyThreadId;
7597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias AgopianIPCThreadState::~IPCThreadState()
7627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
7637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::sendReply(const Parcel& reply, uint32_t flags)
7667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
7677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t err;
7687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t statusBuffer;
769d39a168ff68941c13c5bfc78b5d113c22ef0fd51Martijn Coenen    err = writeTransactionData(BC_REPLY_SG, flags, -1, 0, reply, &statusBuffer);
7707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (err < NO_ERROR) return err;
771dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return waitForResponse(NULL, NULL);
7737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
7747922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::waitForResponse(Parcel *reply, status_t *acquireResult)
7767922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
777b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer    uint32_t cmd;
7787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    int32_t err;
7797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    while (1) {
7817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if ((err=talkWithDriver()) < NO_ERROR) break;
7827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        err = mIn.errorCheck();
7837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (err < NO_ERROR) break;
7847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (mIn.dataAvail() == 0) continue;
785dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
786b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer        cmd = (uint32_t)mIn.readInt32();
787dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7887922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_COMMANDS() {
7897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "Processing waitForResponse Command: "
7907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                << getReturnString(cmd) << endl;
7917922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
7927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
7937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        switch (cmd) {
7947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_TRANSACTION_COMPLETE:
7957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if (!reply && !acquireResult) goto finish;
7967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            break;
797dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
7987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_DEAD_REPLY:
7997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = DEAD_OBJECT;
8007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            goto finish;
8017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_FAILED_REPLY:
8037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = FAILED_TRANSACTION;
8047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            goto finish;
805dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_ACQUIRE_RESULT:
8077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            {
808d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block                ALOG_ASSERT(acquireResult != NULL, "Unexpected brACQUIRE_RESULT");
8097922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                const int32_t result = mIn.readInt32();
8107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                if (!acquireResult) continue;
8117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                *acquireResult = result ? NO_ERROR : INVALID_OPERATION;
8127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
8137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            goto finish;
814dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        case BR_REPLY:
8167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            {
8177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                binder_transaction_data tr;
8187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                err = mIn.read(&tr, sizeof(tr));
819d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block                ALOG_ASSERT(err == NO_ERROR, "Not enough command data for brREPLY");
8207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                if (err != NO_ERROR) goto finish;
8217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                if (reply) {
8237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    if ((tr.flags & TF_STATUS_CODE) == 0) {
8247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                        reply->ipcSetDataReference(
8257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                            reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
8267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                            tr.data_size,
827a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                            reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
828a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                            tr.offsets_size/sizeof(binder_size_t),
8297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                            freeBuffer, this);
8307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    } else {
831a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                        err = *reinterpret_cast<const status_t*>(tr.data.ptr.buffer);
8327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                        freeBuffer(NULL,
8337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                            reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
8347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                            tr.data_size,
835a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                            reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
836a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                            tr.offsets_size/sizeof(binder_size_t), this);
8377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    }
8387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                } else {
8397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    freeBuffer(NULL,
8407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                        reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
8417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                        tr.data_size,
842a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                        reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
843a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                        tr.offsets_size/sizeof(binder_size_t), this);
8447922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    continue;
8457922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                }
8467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
8477922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            goto finish;
8487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        default:
8507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = executeCommand(cmd);
8517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if (err != NO_ERROR) goto finish;
8527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            break;
8537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
8547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
8557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianfinish:
8577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (err != NO_ERROR) {
8587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (acquireResult) *acquireResult = err;
8597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (reply) reply->setError(err);
8607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mLastError = err;
8617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
862dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return err;
8647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
8657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::talkWithDriver(bool doReceive)
8677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
868597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson    if (mProcess->mDriverFD <= 0) {
869597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson        return -EBADF;
870597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson    }
871dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    binder_write_read bwr;
873dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8747922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // Is the read buffer empty?
8757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const bool needRead = mIn.dataPosition() >= mIn.dataSize();
876dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8777922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // We don't want to write anything if we are still reading
8787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // from data left in the input buffer and the caller
8797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // has requested to read the next data.
8807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const size_t outAvail = (!doReceive || needRead) ? mOut.dataSize() : 0;
881dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
8827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    bwr.write_size = outAvail;
883a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg    bwr.write_buffer = (uintptr_t)mOut.data();
8847922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
8857922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // This is what we'll read.
8867922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (doReceive && needRead) {
8877922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        bwr.read_size = mIn.dataCapacity();
888a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg        bwr.read_buffer = (uintptr_t)mIn.data();
8897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } else {
8907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        bwr.read_size = 0;
891455a70a568f5fa2351d31a64e390246b2e4c4d3eBen Cheng        bwr.read_buffer = 0;
8927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
893457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
8947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    IF_LOG_COMMANDS() {
8957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (outAvail != 0) {
8967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "Sending commands to driver: " << indent;
8977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const void* cmds = (const void*)bwr.write_buffer;
8987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const void* end = ((const uint8_t*)cmds)+bwr.write_size;
8997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << HexDump(cmds, bwr.write_size) << endl;
9007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            while (cmds < end) cmds = printCommand(alog, cmds);
9017922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << dedent;
9027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
9037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        alog << "Size of receive buffer: " << bwr.read_size
9047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            << ", needRead: " << needRead << ", doReceive: " << doReceive << endl;
9057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
906dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
9077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    // Return immediately if there is nothing to do.
9087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if ((bwr.write_size == 0) && (bwr.read_size == 0)) return NO_ERROR;
909457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
9107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    bwr.write_consumed = 0;
9117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    bwr.read_consumed = 0;
9127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t err;
9137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    do {
9147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_COMMANDS() {
9157922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "About to read/write, write size = " << mOut.dataSize() << endl;
9167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
917e5e7055dcbfcabfdd735318a0d712e07544a523aElliott Hughes#if defined(__ANDROID__)
9187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (ioctl(mProcess->mDriverFD, BINDER_WRITE_READ, &bwr) >= 0)
9197922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = NO_ERROR;
9207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        else
9217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            err = -errno;
9227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#else
9237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        err = INVALID_OPERATION;
9247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#endif
925597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson        if (mProcess->mDriverFD <= 0) {
926597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson            err = -EBADF;
927597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson        }
9287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_COMMANDS() {
9297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "Finished read/write, write size = " << mOut.dataSize() << endl;
9307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
9317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } while (err == -EINTR);
932457d51fd623e7572aa0279ef63d8e00a2ace1841Andy McFadden
9337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    IF_LOG_COMMANDS() {
934f04879896beb41f2455017ace482283bc2ef321cColin Cross        alog << "Our err: " << (void*)(intptr_t)err << ", write consumed: "
9357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            << bwr.write_consumed << " (of " << mOut.dataSize()
9360646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                        << "), read consumed: " << bwr.read_consumed << endl;
9377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
9387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
9397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (err >= NO_ERROR) {
9407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (bwr.write_consumed > 0) {
941a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg            if (bwr.write_consumed < mOut.dataSize())
9427922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                mOut.remove(0, bwr.write_consumed);
943b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen            else {
9447922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                mOut.setDataSize(0);
945b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen                processPostWriteDerefs();
946b825372059de634f05ea3a2834b9a7fed0187243Martijn Coenen            }
9477922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
9487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        if (bwr.read_consumed > 0) {
9497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mIn.setDataSize(bwr.read_consumed);
9507922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mIn.setDataPosition(0);
9517922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
9527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_COMMANDS() {
9537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "Remaining data size: " << mOut.dataSize() << endl;
9547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << "Received commands from driver: " << indent;
9557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const void* cmds = mIn.data();
9567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const void* end = mIn.data() + mIn.dataSize();
9577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << HexDump(cmds, mIn.dataSize()) << endl;
9587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            while (cmds < end) cmds = printReturnCommand(alog, cmds);
9597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            alog << dedent;
9607922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
9617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return NO_ERROR;
9627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
963dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
9647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return err;
9657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
9667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
9677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::writeTransactionData(int32_t cmd, uint32_t binderFlags,
9687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    int32_t handle, uint32_t code, const Parcel& data, status_t* statusBuffer)
9697922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
970fd51ebbe7e0a9d1fdb2a205350ecdb2aff801785Martijn Coenen    binder_transaction_data_sg tr_sg;
971678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    /* Don't pass uninitialized stack data to a remote process */
972678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.target.ptr = 0;
973678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.target.handle = handle;
974678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.code = code;
975678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.flags = binderFlags;
976678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.cookie = 0;
977678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.sender_pid = 0;
978678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris    tr_sg.transaction_data.sender_euid = 0;
979dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
9807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    const status_t err = data.errorCheck();
9817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (err == NO_ERROR) {
982678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data_size = data.ipcDataSize();
983678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data.ptr.buffer = data.ipcData();
984678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.offsets_size = data.ipcObjectsCount()*sizeof(binder_size_t);
985678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data.ptr.offsets = data.ipcObjects();
986fd51ebbe7e0a9d1fdb2a205350ecdb2aff801785Martijn Coenen        tr_sg.buffers_size = data.ipcBufferSize();
9877922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } else if (statusBuffer) {
988678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.flags |= TF_STATUS_CODE;
9897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        *statusBuffer = err;
990678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data_size = sizeof(status_t);
991678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data.ptr.buffer = reinterpret_cast<uintptr_t>(statusBuffer);
992678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.offsets_size = 0;
993678434faa9c4e3891d98a0aa4f5d0ad74009cf35Christopher Ferris        tr_sg.transaction_data.data.ptr.offsets = 0;
994fd51ebbe7e0a9d1fdb2a205350ecdb2aff801785Martijn Coenen        tr_sg.buffers_size = 0;
9957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    } else {
9967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        return (mLastError = err);
9977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
998dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
9997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    mOut.writeInt32(cmd);
1000fd51ebbe7e0a9d1fdb2a205350ecdb2aff801785Martijn Coenen    mOut.write(&tr_sg, sizeof(tr_sg));
1001dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return NO_ERROR;
10037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
10047922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1005dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hongvoid IPCThreadState::setTheContextObject(sp<BHwBinder> obj)
10067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
1007a660cbcab5c8c9b53c1d022d8a11a0c384237569Martijn Coenen    mContextObject = obj;
10087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
10097922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1010420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenenbool IPCThreadState::isLooperThread()
1011420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen{
1012420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen    return mIsLooper;
1013420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen}
1014420d4bb0e8977eef2c66a5a88688dbe2e59cd6ebMartijn Coenen
1015a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskogbool IPCThreadState::isOnlyBinderThread() {
1016a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog    return (mIsLooper && mProcess->mMaxThreads <= 1) || mIsPollingThread;
1017a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog}
1018a36d576f20a31a117cb6f5c316e4446ae7b2fa35Tobias Lindskog
10197922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianstatus_t IPCThreadState::executeCommand(int32_t cmd)
10207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
1021dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong    BHwBinder* obj;
10227922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    RefBase::weakref_type* refs;
10237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    status_t result = NO_ERROR;
1024b184ed0c2835773cf75b88b3330653cc4222ce9aBernhard Rosenkränzer    switch ((uint32_t)cmd) {
10257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_ERROR:
10267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        result = mIn.readInt32();
10277922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1028dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_OK:
10307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1031dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_ACQUIRE:
10334ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        refs = (RefBase::weakref_type*)mIn.readPointer();
1034dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        obj = (BHwBinder*)mIn.readPointer();
1035d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block        ALOG_ASSERT(refs->refBase() == obj,
10367922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                   "BR_ACQUIRE: object %p does not match cookie %p (expected %p)",
10377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                   refs, obj, refs->refBase());
10387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        obj->incStrong(mProcess.get());
10397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_REMOTEREFS() {
10407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            LOG_REMOTEREFS("BR_ACQUIRE from driver on %p", obj);
10417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            obj->printRefs();
10427922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
10437922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mOut.writeInt32(BC_ACQUIRE_DONE);
10444ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        mOut.writePointer((uintptr_t)refs);
10454ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        mOut.writePointer((uintptr_t)obj);
10467922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1047dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10487922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_RELEASE:
10494ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        refs = (RefBase::weakref_type*)mIn.readPointer();
1050dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        obj = (BHwBinder*)mIn.readPointer();
1051d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block        ALOG_ASSERT(refs->refBase() == obj,
10527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                   "BR_RELEASE: object %p does not match cookie %p (expected %p)",
10537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                   refs, obj, refs->refBase());
10547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        IF_LOG_REMOTEREFS() {
10557922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            LOG_REMOTEREFS("BR_RELEASE from driver on %p", obj);
10567922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            obj->printRefs();
10577922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
10587922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mPendingStrongDerefs.push(obj);
10597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1060dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_INCREFS:
10624ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        refs = (RefBase::weakref_type*)mIn.readPointer();
1063dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        obj = (BHwBinder*)mIn.readPointer();
10647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        refs->incWeak(mProcess.get());
10657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mOut.writeInt32(BC_INCREFS_DONE);
10664ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        mOut.writePointer((uintptr_t)refs);
10674ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        mOut.writePointer((uintptr_t)obj);
10687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1069dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_DECREFS:
10714ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        refs = (RefBase::weakref_type*)mIn.readPointer();
1072dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        obj = (BHwBinder*)mIn.readPointer();
10737922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // NOTE: This assertion is not valid, because the object may no
1074dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        // longer exist (thus the (BHwBinder*)cast above resulting in a different
10757922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        // memory address).
1076d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block        //ALOG_ASSERT(refs->refBase() == obj,
10777922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        //           "BR_DECREFS: object %p does not match cookie %p (expected %p)",
10787922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        //           refs, obj, refs->refBase());
10797922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mPendingWeakDerefs.push(refs);
10807922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1081dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10827922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_ATTEMPT_ACQUIRE:
10834ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu        refs = (RefBase::weakref_type*)mIn.readPointer();
1084dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong        obj = (BHwBinder*)mIn.readPointer();
1085dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10867922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        {
10877922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const bool success = refs->attemptIncStrong(mProcess.get());
1088d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block            ALOG_ASSERT(success && refs->refBase() == obj,
10897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                       "BR_ATTEMPT_ACQUIRE: object %p does not match cookie %p (expected %p)",
10907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                       refs, obj, refs->refBase());
1091dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10927922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mOut.writeInt32(BC_ACQUIRE_RESULT);
10937922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mOut.writeInt32((int32_t)success);
10947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
10957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1096dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
10977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_TRANSACTION:
10987922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        {
10997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            binder_transaction_data tr;
11007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            result = mIn.read(&tr, sizeof(tr));
1101d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block            ALOG_ASSERT(result == NO_ERROR,
11027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                "Not enough command data for brTRANSACTION");
11037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if (result != NO_ERROR) break;
1104dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
11057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            Parcel buffer;
11067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            buffer.ipcSetDataReference(
11077922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer),
11087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                tr.data_size,
1109a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                reinterpret_cast<const binder_size_t*>(tr.data.ptr.offsets),
1110a544070681ccced272b4fa3b5781096cba05dde5Arve Hjønnevåg                tr.offsets_size/sizeof(binder_size_t), freeBuffer, this);
1111dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
11127922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const pid_t origPid = mCallingPid;
11137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            const uid_t origUid = mCallingUid;
1114f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            const int32_t origStrictModePolicy = mStrictModePolicy;
1115f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            const int32_t origTransactionBinderFlags = mLastTransactionBinderFlags;
1116f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn
11177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mCallingPid = tr.sender_pid;
11187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mCallingUid = tr.sender_euid;
1119f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            mLastTransactionBinderFlags = tr.flags;
1120f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn
112193cf854f5e563ba575691b4b639365fe6c517193Steve Block            //ALOGI(">>>> TRANSACT from pid %d uid %d\n", mCallingPid, mCallingUid);
1122f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn
11237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            Parcel reply;
1124f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            status_t error;
112579c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen            bool reply_sent = false;
11267922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            IF_LOG_TRANSACTIONS() {
11277922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                alog << "BR_TRANSACTION thr " << (void*)pthread_self()
11287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << " / obj " << tr.target.ptr << " / code "
11297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << TypeCode(tr.code) << ": " << indent << buffer
11307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << dedent << endl
11317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << "Data addr = "
11327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer)
11337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << ", offsets addr="
11347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << reinterpret_cast<const size_t*>(tr.data.ptr.offsets) << endl;
11357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
113679c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen
113779c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen            auto reply_callback = [&] (auto &replyParcel) {
113879c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                if (reply_sent) {
113979c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    // Reply was sent earlier, ignore it.
114079c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    ALOGE("Dropping binder reply, it was sent already.");
114179c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    return;
114279c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                }
114379c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                reply_sent = true;
114479c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                if ((tr.flags & TF_ONE_WAY) == 0) {
114579c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    replyParcel.setError(NO_ERROR);
114679c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    sendReply(replyParcel, 0);
114779c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                } else {
114879c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    ALOGE("Not sending reply in one-way transaction");
114979c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                }
115079c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen            };
115179c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen
11527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if (tr.target.ptr) {
1153839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                // We only have a weak reference on the target object, so we must first try to
1154839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                // safely acquire a strong reference before doing anything else with it.
1155839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                if (reinterpret_cast<RefBase::weakref_type*>(
1156839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                        tr.target.ptr)->attemptIncStrong(this)) {
1157dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong                    error = reinterpret_cast<BHwBinder*>(tr.cookie)->transact(tr.code, buffer,
115879c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                            &reply, tr.flags, reply_callback);
1159dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong                    reinterpret_cast<BHwBinder*>(tr.cookie)->decStrong(this);
1160839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                } else {
1161839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                    error = UNKNOWN_TRANSACTION;
1162839f707a38ed15685da48bbd5f4458817b5a54c6Dianne Hackborn                }
116324f8bca9cb9778ae67a3642108d4ab67eca642f8Brad Fitzpatrick
11647922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            } else {
1165a660cbcab5c8c9b53c1d022d8a11a0c384237569Martijn Coenen                error = mContextObject->transact(tr.code, buffer, &reply, tr.flags, reply_callback);
11667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
1167f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn
11687922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            if ((tr.flags & TF_ONE_WAY) == 0) {
116979c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                if (!reply_sent) {
117079c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    // Should have been a reply but there wasn't, so there
117179c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    // must have been an error instead.
117279c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    reply.setError(error);
117379c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    sendReply(reply, 0);
117479c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                } else {
117579c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    if (error != NO_ERROR) {
117679c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                        ALOGE("transact() returned error after sending reply.");
117779c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    } else {
117879c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                        // Ok, reply sent and transact didn't return an error.
117979c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                    }
118079c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                }
11817922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            } else {
118279c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen                // One-way transaction, don't care about return value or reply.
11837922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
118479c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen
118579c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen            //ALOGI("<<<< TRANSACT from pid %d restore pid %d uid %d\n",
118679c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen            //     mCallingPid, origPid, origUid);
118779c2f4d38c83ac8fe4c9c77e98e04f310016e7a6Martijn Coenen
1188dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
11897922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mCallingPid = origPid;
11907922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mCallingUid = origUid;
1191f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            mStrictModePolicy = origStrictModePolicy;
1192f99aec6a0cff674e0a010cf5789beb4cf4be592dDianne Hackborn            mLastTransactionBinderFlags = origTransactionBinderFlags;
11937c4dfece81abcf7d67b747ce25d452b150f9e9cbChristopher Tate
11947922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            IF_LOG_TRANSACTIONS() {
11957922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                alog << "BC_REPLY thr " << (void*)pthread_self() << " / obj "
11967922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian                    << tr.target.ptr << ": " << indent << reply << dedent << endl;
11977922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            }
1198dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
11997922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        }
12007922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1201dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12027922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_DEAD_BINDER:
12037922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        {
12041e118d2b86540f7a7d840ec1510337da49f1446cYifan Hong            BpHwBinder *proxy = (BpHwBinder*)mIn.readPointer();
12057922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            proxy->sendObituary();
12067922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            mOut.writeInt32(BC_DEAD_BINDER_DONE);
12074ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu            mOut.writePointer((uintptr_t)proxy);
12087922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
1209dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12107922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_CLEAR_DEATH_NOTIFICATION_DONE:
12117922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        {
12121e118d2b86540f7a7d840ec1510337da49f1446cYifan Hong            BpHwBinder *proxy = (BpHwBinder*)mIn.readPointer();
12137922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian            proxy->getWeakRefs()->decWeak(proxy);
12147922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        } break;
1215dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12167922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_FINISHED:
12177922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        result = TIMED_OUT;
12187922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1219dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12207922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_NOOP:
12217922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1222dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12237922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    case BR_SPAWN_LOOPER:
12247922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mProcess->spawnPooledThread(false);
12257922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
1226dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12277922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    default:
12287922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        printf("*** BAD COMMAND %d received from Binder driver\n", cmd);
12297922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        result = UNKNOWN_ERROR;
12307922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        break;
12317922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
12327922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
12337922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (result != NO_ERROR) {
12347922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        mLastError = result;
12357922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
1236dde40f31347a51aa7249cb192f97276c30d984f5Yifan Hong
12377922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    return result;
12387922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
12397922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
12407922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopianvoid IPCThreadState::threadDestructor(void *st)
12417922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
12420646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        IPCThreadState* const self = static_cast<IPCThreadState*>(st);
12430646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        if (self) {
12440646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                self->flushCommands();
1245e5e7055dcbfcabfdd735318a0d712e07544a523aElliott Hughes#if defined(__ANDROID__)
1246597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson        if (self->mProcess->mDriverFD > 0) {
1247597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson            ioctl(self->mProcess->mDriverFD, BINDER_THREAD_EXIT, 0);
1248597a3c7696af00cc4c3e6d919c507adc552cdfd7Johannes Carlsson        }
12497922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian#endif
12500646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor                delete self;
12510646cb013e216d9f1fcd76365d07f369af8b989dTodd Poynor        }
12527922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
12537922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
12547922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1255f04879896beb41f2455017ace482283bc2ef321cColin Crossvoid IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data,
1256f04879896beb41f2455017ace482283bc2ef321cColin Cross                                size_t /*dataSize*/,
1257f04879896beb41f2455017ace482283bc2ef321cColin Cross                                const binder_size_t* /*objects*/,
1258f04879896beb41f2455017ace482283bc2ef321cColin Cross                                size_t /*objectsSize*/, void* /*cookie*/)
12597922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian{
126093cf854f5e563ba575691b4b639365fe6c517193Steve Block    //ALOGI("Freeing parcel %p", &parcel);
12617922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    IF_LOG_COMMANDS() {
12627922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian        alog << "Writing BC_FREE_BUFFER for " << data << endl;
12637922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    }
1264d0bfabc8c2b42ca8f71f066b8a6de2e8f7995203Steve Block    ALOG_ASSERT(data != NULL, "Called with NULL data");
12657922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    if (parcel != NULL) parcel->closeFileDescriptors();
12667922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    IPCThreadState* state = self();
12677922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian    state->mOut.writeInt32(BC_FREE_BUFFER);
12684ca5bafb8da8e2316464be178f32a170b494300bSerban Constantinescu    state->mOut.writePointer((uintptr_t)data);
12697922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}
12707922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian
1271f75a23d54cc9e5f7b6b976e65b6ec346178f306dMartijn Coenen}; // namespace hardware
12727922fa29f3a18386b6eb4cb19e8c582d9f751345Mathias Agopian}; // namespace android
1273