Android Process & Thread
Native Service and Android Service
- Native Service:In every main() method of NativeService, which is called by init process through parseing init.rc, the globale object of ProcessState will be created by calling ProcessState::self(),and then startThreadPool and created main thread by calling IPCThreadPool.self()->joinThreadPool().
- Android Service:All Android Service is created by SystemServer and running in the same process which is system server.
New Process with main()
1 int main(int argc, char** argv) 2 { 3 sp<ProcessState> proc(ProcessState::self()); 4 sp<IServiceManager> sm = defaultServiceManager(); 5 LOGI("ServiceManager: %p", sm.get()); 6 AudioFlinger::instantiate(); 7 MediaPlayerService::instantiate(); 8 CameraService::instantiate(); 9 AudioPolicyService::instantiate(); 10 ProcessState::self()->startThreadPool(); 11 IPCThreadState::self()->joinThreadPool(); 12 }
Static: private/binder/Static.h
- Static.h
-
1 #include <utils/threads.h> 2 #include <binder/IBinder.h> 3 #include <binder/IMemory.h> 4 #include <binder/ProcessState.h> 5 #include <binder/IPermissionController.h> 6 #include <binder/IServiceManager.h> 7 namespace android { 8 // For ProcessState.cpp 9 extern Mutex gProcessMutex; 10 extern sp<ProcessState> gProcess; 11 // For ServiceManager.cpp 12 extern Mutex gDefaultServiceManagerLock; 13 extern sp<IServiceManager> gDefaultServiceManager; 14 extern sp<IPermissionController> gPermissionController; 15 }
- Static.cpp
-
1 #include <private/binder/Static.h> 2 #include <binder/IPCThreadState.h> 3 #include <utils/Log.h> 4 namespace android { 5 // ------------ ProcessState.cpp 6 Mutex gProcessMutex; 7 sp<ProcessState> gProcess; 8 class LibUtilsIPCtStatics 9 { 10 public: 11 LibUtilsIPCtStatics() 12 { 13 } 14 15 ~LibUtilsIPCtStatics() 16 { 17 IPCThreadState::shutdown(); 18 } 19 }; 20 static LibUtilsIPCtStatics gIPCStatics; 21 // ------------ ServiceManager.cpp 22 Mutex gDefaultServiceManagerLock; 23 sp<IServiceManager> gDefaultServiceManager; 24 sp<IPermissionController> gPermissionController; 25 }
- When we create new process and call main()..........,the gloable vairables will be created
-
Mutex gProcessMutex; sp<ProcessState> gProcess; Mutex gDefaultServiceManagerLock; sp<IServiceManager> gDefaultServiceManager; sp<IPermissionController> gPermissionController;
Threads
- android.threads wrap something related to thread using linux's pthread.h
-
1 /** 2 * Copyright (C) 2007 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef _LIBS_UTILS_THREADS_H 18 #define _LIBS_UTILS_THREADS_H 19 20 #include <stdint.h> 21 #include <sys/types.h> 22 #include <time.h> 23 #include <system/graphics.h> 24 25 #if defined(HAVE_PTHREADS) 26 # include <pthread.h> 27 #endif 28 29 // ------------------------------------------------------------------ 30 // C API 31 32 #ifdef __cplusplus 33 extern "C" { 34 #endif 35 36 typedef void* android_thread_id_t; 37 38 typedef int (*android_thread_func_t)(void*); 39 40 enum { 41 /** 42 * *********************************************** 43 * ** Keep in sync with android.os.Process.java ** 44 * *********************************************** 45 * 46 * This maps directly to the "nice" priorities we use in Android. 47 * A thread priority should be chosen inverse-proportionally to 48 * the amount of work the thread is expected to do. The more work 49 * a thread will do, the less favorable priority it should get so that 50 * it doesn't starve the system. Threads not behaving properly might 51 * be "punished" by the kernel. 52 * Use the levels below when appropriate. Intermediate values are 53 * acceptable, preferably use the {MORE|LESS}_FAVORABLE constants below. 54 */ 55 ANDROID_PRIORITY_LOWEST = 19, 56 57 /** use for background tasks */ 58 ANDROID_PRIORITY_BACKGROUND = 10, 59 60 /** most threads run at normal priority */ 61 ANDROID_PRIORITY_NORMAL = 0, 62 63 /** threads currently running a UI that the user is interacting with */ 64 ANDROID_PRIORITY_FOREGROUND = -2, 65 66 /** the main UI thread has a slightly more favorable priority */ 67 ANDROID_PRIORITY_DISPLAY = -4, 68 69 /** ui service treads might want to run at a urgent display (uncommon) */ 70 ANDROID_PRIORITY_URGENT_DISPLAY = HAL_PRIORITY_URGENT_DISPLAY, 71 72 /** all normal audio threads */ 73 ANDROID_PRIORITY_AUDIO = -16, 74 75 /** service audio threads (uncommon) */ 76 ANDROID_PRIORITY_URGENT_AUDIO = -19, 77 78 /** should never be used in practice. regular process might not 79 * be allowed to use this level */ 80 ANDROID_PRIORITY_HIGHEST = -20, 81 82 ANDROID_PRIORITY_DEFAULT = ANDROID_PRIORITY_NORMAL, 83 ANDROID_PRIORITY_MORE_FAVORABLE = -1, 84 ANDROID_PRIORITY_LESS_FAVORABLE = +1, 85 }; 86 87 enum { 88 ANDROID_TGROUP_DEFAULT = 0, 89 ANDROID_TGROUP_BG_NONINTERACT = 1, 90 ANDROID_TGROUP_FG_BOOST = 2, 91 ANDROID_TGROUP_MAX = ANDROID_TGROUP_FG_BOOST, 92 }; 93 94 // Create and run a new thread. 95 extern int androidCreateThread(android_thread_func_t, void *); 96 97 // Create thread with lots of parameters 98 extern int androidCreateThreadEtc(android_thread_func_t entryFunction, 99 void *userData, 100 const char* threadName, 101 int32_t threadPriority, 102 size_t threadStackSize, 103 android_thread_id_t *threadId); 104 105 // Get some sort of unique identifier for the current thread. 106 extern android_thread_id_t androidGetThreadId(); 107 108 // Low-level thread creation -- never creates threads that can 109 // interact with the Java VM. 110 extern int androidCreateRawThreadEtc(android_thread_func_t entryFunction, 111 void *userData, 112 const char* threadName, 113 int32_t threadPriority, 114 size_t threadStackSize, 115 android_thread_id_t *threadId); 116 117 // Used by the Java Runtime to control how threads are created, so that 118 // they can be proper and lovely Java threads. 119 typedef int (*android_create_thread_fn)(android_thread_func_t entryFunction, 120 void *userData, 121 const char* threadName, 122 int32_t threadPriority, 123 size_t threadStackSize, 124 android_thread_id_t *threadId); 125 126 extern void androidSetCreateThreadFunc(android_create_thread_fn func); 127 128 // ------------------------------------------------------------------ 129 // Extra functions working with raw pids. 130 131 // Get pid for the current thread. 132 extern pid_t androidGetTid(); 133 134 // Change the scheduling group of a particular thread. The group 135 // should be one of the ANDROID_TGROUP constants. Returns BAD_VALUE if 136 // grp is out of range, else another non-zero value with errno set if 137 // the operation failed. Thread ID zero means current thread. 138 extern int androidSetThreadSchedulingGroup(pid_t tid, int grp); 139 140 // Change the priority AND scheduling group of a particular thread. The priority 141 // should be one of the ANDROID_PRIORITY constants. Returns INVALID_OPERATION 142 // if the priority set failed, else another value if just the group set failed; 143 // in either case errno is set. Thread ID zero means current thread. 144 extern int androidSetThreadPriority(pid_t tid, int prio); 145 146 // Get the current priority of a particular thread. Returns one of the 147 // ANDROID_PRIORITY constants or a negative result in case of error. 148 extern int androidGetThreadPriority(pid_t tid); 149 150 // Get the current scheduling group of a particular thread. Normally returns 151 // one of the ANDROID_TGROUP constants other than ANDROID_TGROUP_DEFAULT. 152 // Returns ANDROID_TGROUP_DEFAULT if no pthread support (e.g. on host) or if 153 // scheduling groups are disabled. Returns INVALID_OPERATION if unexpected error. 154 // Thread ID zero means current thread. 155 extern int androidGetThreadSchedulingGroup(pid_t tid); 156 157 #ifdef __cplusplus 158 } 159 #endif 160 161 // ------------------------------------------------------------------ 162 // C++ API 163 164 #ifdef __cplusplus 165 166 #include <utils/Errors.h> 167 #include <utils/RefBase.h> 168 #include <utils/Timers.h> 169 170 namespace android { 171 172 typedef android_thread_id_t thread_id_t; 173 174 typedef android_thread_func_t thread_func_t; 175 176 enum { 177 PRIORITY_LOWEST = ANDROID_PRIORITY_LOWEST, 178 PRIORITY_BACKGROUND = ANDROID_PRIORITY_BACKGROUND, 179 PRIORITY_NORMAL = ANDROID_PRIORITY_NORMAL, 180 PRIORITY_FOREGROUND = ANDROID_PRIORITY_FOREGROUND, 181 PRIORITY_DISPLAY = ANDROID_PRIORITY_DISPLAY, 182 PRIORITY_URGENT_DISPLAY = ANDROID_PRIORITY_URGENT_DISPLAY, 183 PRIORITY_AUDIO = ANDROID_PRIORITY_AUDIO, 184 PRIORITY_URGENT_AUDIO = ANDROID_PRIORITY_URGENT_AUDIO, 185 PRIORITY_HIGHEST = ANDROID_PRIORITY_HIGHEST, 186 PRIORITY_DEFAULT = ANDROID_PRIORITY_DEFAULT, 187 PRIORITY_MORE_FAVORABLE = ANDROID_PRIORITY_MORE_FAVORABLE, 188 PRIORITY_LESS_FAVORABLE = ANDROID_PRIORITY_LESS_FAVORABLE, 189 }; 190 191 // Create and run a new thread. 192 inline bool createThread(thread_func_t f, void *a) { 193 return androidCreateThread(f, a) ? true : false; 194 } 195 196 // Create thread with lots of parameters 197 inline bool createThreadEtc(thread_func_t entryFunction, 198 void *userData, 199 const char* threadName = "android:unnamed_thread", 200 int32_t threadPriority = PRIORITY_DEFAULT, 201 size_t threadStackSize = 0, 202 thread_id_t *threadId = 0) 203 { 204 return androidCreateThreadEtc(entryFunction, userData, threadName, 205 threadPriority, threadStackSize, threadId) ? true : false; 206 } 207 208 // Get some sort of unique identifier for the current thread. 209 inline thread_id_t getThreadId() { 210 return androidGetThreadId(); 211 } 212 213 /******************************************************************************/ 214 215 /** 216 * Simple mutex class. The implementation is system-dependent. 217 * 218 * The mutex must be unlocked by the thread that locked it. They are not 219 * recursive, i.e. the same thread can't lock it multiple times. 220 */ 221 class Mutex { 222 public: 223 enum { 224 PRIVATE = 0, 225 SHARED = 1 226 }; 227 228 Mutex(); 229 Mutex(const char* name); 230 Mutex(int type, const char* name = NULL); 231 ~Mutex(); 232 233 // lock or unlock the mutex 234 status_t lock(); 235 void unlock(); 236 237 // lock if possible; returns 0 on success, error otherwise 238 status_t tryLock(); 239 240 // Manages the mutex automatically. It'll be locked when Autolock is 241 // constructed and released when Autolock goes out of scope. 242 class Autolock { 243 public: 244 inline Autolock(Mutex& mutex) : mLock(mutex) { mLock.lock(); } 245 inline Autolock(Mutex* mutex) : mLock(*mutex) { mLock.lock(); } 246 inline ~Autolock() { mLock.unlock(); } 247 private: 248 Mutex& mLock; 249 }; 250 251 private: 252 friend class Condition; 253 254 // A mutex cannot be copied 255 Mutex(const Mutex&); 256 Mutex& operator = (const Mutex&); 257 258 #if defined(HAVE_PTHREADS) 259 pthread_mutex_t mMutex; 260 #else 261 void _init(); 262 void* mState; 263 #endif 264 }; 265 266 #if defined(HAVE_PTHREADS) 267 268 inline Mutex::Mutex() { 269 pthread_mutex_init(&mMutex, NULL); 270 } 271 inline Mutex::Mutex(const char* name) { 272 pthread_mutex_init(&mMutex, NULL); 273 } 274 inline Mutex::Mutex(int type, const char* name) { 275 if (type == SHARED) { 276 pthread_mutexattr_t attr; 277 pthread_mutexattr_init(&attr); 278 pthread_mutexattr_setpshared(&attr, PTHREAD_PROCESS_SHARED); 279 pthread_mutex_init(&mMutex, &attr); 280 pthread_mutexattr_destroy(&attr); 281 } else { 282 pthread_mutex_init(&mMutex, NULL); 283 } 284 } 285 inline Mutex::~Mutex() { 286 pthread_mutex_destroy(&mMutex); 287 } 288 inline status_t Mutex::lock() { 289 return -pthread_mutex_lock(&mMutex); 290 } 291 inline void Mutex::unlock() { 292 pthread_mutex_unlock(&mMutex); 293 } 294 inline status_t Mutex::tryLock() { 295 return -pthread_mutex_trylock(&mMutex); 296 } 297 298 #endif // HAVE_PTHREADS 299 300 /** 301 * Automatic mutex. Declare one of these at the top of a function. 302 * When the function returns, it will go out of scope, and release the 303 * mutex. 304 */ 305 306 typedef Mutex::Autolock AutoMutex; 307 308 /******************************************************************************/ 309 310 #if defined(HAVE_PTHREADS) 311 312 /** 313 * Simple mutex class. The implementation is system-dependent. 314 * 315 * The mutex must be unlocked by the thread that locked it. They are not 316 * recursive, i.e. the same thread can't lock it multiple times. 317 */ 318 class RWLock { 319 public: 320 enum { 321 PRIVATE = 0, 322 SHARED = 1 323 }; 324 325 RWLock(); 326 RWLock(const char* name); 327 RWLock(int type, const char* name = NULL); 328 ~RWLock(); 329 330 status_t readLock(); 331 status_t tryReadLock(); 332 status_t writeLock(); 333 status_t tryWriteLock(); 334 void unlock(); 335 336 class AutoRLock { 337 public: 338 inline AutoRLock(RWLock& rwlock) : mLock(rwlock) { mLock.readLock(); } 339 inline ~AutoRLock() { mLock.unlock(); } 340 private: 341 RWLock& mLock; 342 }; 343 344 class AutoWLock { 345 public: 346 inline AutoWLock(RWLock& rwlock) : mLock(rwlock) { mLock.writeLock(); } 347 inline ~AutoWLock() { mLock.unlock(); } 348 private: 349 RWLock& mLock; 350 }; 351 352 private: 353 // A RWLock cannot be copied 354 RWLock(const RWLock&); 355 RWLock& operator = (const RWLock&); 356 357 pthread_rwlock_t mRWLock; 358 }; 359 360 inline RWLock::RWLock() { 361 pthread_rwlock_init(&mRWLock, NULL); 362 } 363 inline RWLock::RWLock(const char* name) { 364 pthread_rwlock_init(&mRWLock, NULL); 365 } 366 inline RWLock::RWLock(int type, const char* name) { 367 if (type == SHARED) { 368 pthread_rwlockattr_t attr; 369 pthread_rwlockattr_init(&attr); 370 pthread_rwlockattr_setpshared(&attr, PTHREAD_PROCESS_SHARED); 371 pthread_rwlock_init(&mRWLock, &attr); 372 pthread_rwlockattr_destroy(&attr); 373 } else { 374 pthread_rwlock_init(&mRWLock, NULL); 375 } 376 } 377 inline RWLock::~RWLock() { 378 pthread_rwlock_destroy(&mRWLock); 379 } 380 inline status_t RWLock::readLock() { 381 return -pthread_rwlock_rdlock(&mRWLock); 382 } 383 inline status_t RWLock::tryReadLock() { 384 return -pthread_rwlock_tryrdlock(&mRWLock); 385 } 386 inline status_t RWLock::writeLock() { 387 return -pthread_rwlock_wrlock(&mRWLock); 388 } 389 inline status_t RWLock::tryWriteLock() { 390 return -pthread_rwlock_trywrlock(&mRWLock); 391 } 392 inline void RWLock::unlock() { 393 pthread_rwlock_unlock(&mRWLock); 394 } 395 396 #endif // HAVE_PTHREADS 397 398 /******************************************************************************/ 399 400 /** 401 * Condition variable class. The implementation is system-dependent. 402 * 403 * Condition variables are paired up with mutexes. Lock the mutex, 404 * call wait(), then either re-wait() if things aren't quite what you want, 405 * or unlock the mutex and continue. All threads calling wait() must 406 * use the same mutex for a given Condition. 407 */ 408 class Condition { 409 public: 410 enum { 411 PRIVATE = 0, 412 SHARED = 1 413 }; 414 415 Condition(); 416 Condition(int type); 417 ~Condition(); 418 // Wait on the condition variable. Lock the mutex before calling. 419 status_t wait(Mutex& mutex); 420 // same with relative timeout 421 status_t waitRelative(Mutex& mutex, nsecs_t reltime); 422 // Signal the condition variable, allowing one thread to continue. 423 void signal(); 424 // Signal the condition variable, allowing all threads to continue. 425 void broadcast(); 426 427 private: 428 #if defined(HAVE_PTHREADS) 429 pthread_cond_t mCond; 430 #else 431 void* mState; 432 #endif 433 }; 434 435 #if defined(HAVE_PTHREADS) 436 437 inline Condition::Condition() { 438 pthread_cond_init(&mCond, NULL); 439 } 440 inline Condition::Condition(int type) { 441 if (type == SHARED) { 442 pthread_condattr_t attr; 443 pthread_condattr_init(&attr); 444 pthread_condattr_setpshared(&attr, PTHREAD_PROCESS_SHARED); 445 pthread_cond_init(&mCond, &attr); 446 pthread_condattr_destroy(&attr); 447 } else { 448 pthread_cond_init(&mCond, NULL); 449 } 450 } 451 inline Condition::~Condition() { 452 pthread_cond_destroy(&mCond); 453 } 454 inline status_t Condition::wait(Mutex& mutex) { 455 return -pthread_cond_wait(&mCond, &mutex.mMutex); 456 } 457 inline status_t Condition::waitRelative(Mutex& mutex, nsecs_t reltime) { 458 #if defined(HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE) 459 struct timespec ts; 460 ts.tv_sec = reltime/1000000000; 461 ts.tv_nsec = reltime%1000000000; 462 return -pthread_cond_timedwait_relative_np(&mCond, &mutex.mMutex, &ts); 463 #else // HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE 464 struct timespec ts; 465 #if defined(HAVE_POSIX_CLOCKS) 466 clock_gettime(CLOCK_REALTIME, &ts); 467 #else // HAVE_POSIX_CLOCKS 468 // we don't support the clocks here. 469 struct timeval t; 470 gettimeofday(&t, NULL); 471 ts.tv_sec = t.tv_sec; 472 ts.tv_nsec= t.tv_usec*1000; 473 #endif // HAVE_POSIX_CLOCKS 474 ts.tv_sec += reltime/1000000000; 475 ts.tv_nsec+= reltime%1000000000; 476 if (ts.tv_nsec >= 1000000000) { 477 ts.tv_nsec -= 1000000000; 478 ts.tv_sec += 1; 479 } 480 return -pthread_cond_timedwait(&mCond, &mutex.mMutex, &ts); 481 #endif // HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE 482 } 483 inline void Condition::signal() { 484 pthread_cond_signal(&mCond); 485 } 486 inline void Condition::broadcast() { 487 pthread_cond_broadcast(&mCond); 488 } 489 490 #endif // HAVE_PTHREADS 491 492 /******************************************************************************/ 493 494 /** 495 * This is our spiffy thread object! 496 */ 497 498 class Thread : virtual public RefBase 499 { 500 public: 501 // Create a Thread object, but doesn't create or start the associated 502 // thread. See the run() method. 503 Thread(bool canCallJava = true); 504 virtual ~Thread(); 505 506 // Start the thread in threadLoop() which needs to be implemented. 507 virtual status_t run( const char* name = 0, 508 int32_t priority = PRIORITY_DEFAULT, 509 size_t stack = 0); 510 511 // Ask this object's thread to exit. This function is asynchronous, when the 512 // function returns the thread might still be running. Of course, this 513 // function can be called from a different thread. 514 virtual void requestExit(); 515 516 // Good place to do one-time initializations 517 virtual status_t readyToRun(); 518 519 // Call requestExit() and wait until this object's thread exits. 520 // BE VERY CAREFUL of deadlocks. In particular, it would be silly to call 521 // this function from this object's thread. Will return WOULD_BLOCK in 522 // that case. 523 status_t requestExitAndWait(); 524 525 // Wait until this object's thread exits. Returns immediately if not yet running. 526 // Do not call from this object's thread; will return WOULD_BLOCK in that case. 527 status_t join(); 528 529 protected: 530 // exitPending() returns true if requestExit() has been called. 531 bool exitPending() const; 532 533 private: 534 // Derived class must implement threadLoop(). The thread starts its life 535 // here. There are two ways of using the Thread object: 536 // 1) loop: if threadLoop() returns true, it will be called again if 537 // requestExit() wasn't called. 538 // 2) once: if threadLoop() returns false, the thread will exit upon return. 539 virtual bool threadLoop() = 0; 540 541 private: 542 Thread& operator=(const Thread&); 543 static int _threadLoop(void* user); 544 const bool mCanCallJava; 545 // always hold mLock when reading or writing 546 thread_id_t mThread; 547 mutable Mutex mLock; 548 Condition mThreadExitedCondition; 549 status_t mStatus; 550 // note that all accesses of mExitPending and mRunning need to hold mLock 551 volatile bool mExitPending; 552 volatile bool mRunning; 553 sp<Thread> mHoldSelf; 554 #if HAVE_ANDROID_OS 555 int mTid; 556 #endif 557 }; 558 559 560 }; // namespace android 561 562 #endif // __cplusplus 563 564 #endif // _LIBS_UTILS_THREADS_H
-
1 /** 2 * Copyright (C) 2007 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 // #define LOG_NDEBUG 0 18 #define LOG_TAG "libutils.threads" 19 20 #include <utils/threads.h> 21 #include <utils/Log.h> 22 23 #include <cutils/sched_policy.h> 24 #include <cutils/properties.h> 25 26 #include <stdio.h> 27 #include <stdlib.h> 28 #include <memory.h> 29 #include <errno.h> 30 #include <assert.h> 31 #include <unistd.h> 32 33 #if defined(HAVE_PTHREADS) 34 # include <pthread.h> 35 # include <sched.h> 36 # include <sys/resource.h> 37 #elif defined(HAVE_WIN32_THREADS) 38 # include <windows.h> 39 # include <stdint.h> 40 # include <process.h> 41 # define HAVE_CREATETHREAD // Cygwin, vs. HAVE__BEGINTHREADEX for MinGW 42 #endif 43 44 #if defined(HAVE_PRCTL) 45 #include <sys/prctl.h> 46 #endif 47 48 /** 49 * =========================================================================== 50 * Thread wrappers 51 * =========================================================================== 52 */ 53 54 using namespace android; 55 56 // ---------------------------------------------------------------------------- 57 #if defined(HAVE_PTHREADS) 58 // ---------------------------------------------------------------------------- 59 60 /** 61 * Create and run a new thread. 62 * 63 * We create it "detached", so it cleans up after itself. 64 */ 65 66 typedef void* (*android_pthread_entry)(void*); 67 68 static pthread_once_t gDoSchedulingGroupOnce = PTHREAD_ONCE_INIT; 69 static bool gDoSchedulingGroup = true; 70 71 static void checkDoSchedulingGroup(void) { 72 char buf[PROPERTY_VALUE_MAX]; 73 int len = property_get("debug.sys.noschedgroups", buf, ""); 74 if (len > 0) { 75 int temp; 76 if (sscanf(buf, "%d", &temp) == 1) { 77 gDoSchedulingGroup = temp == 0; 78 } 79 } 80 } 81 82 struct thread_data_t { 83 thread_func_t entryFunction; 84 void* userData; 85 int priority; 86 char * threadName; 87 88 // we use this trampoline when we need to set the priority with 89 // nice/setpriority. 90 static int trampoline(const thread_data_t* t) { 91 thread_func_t f = t->entryFunction; 92 void* u = t->userData; 93 int prio = t->priority; 94 char * name = t->threadName; 95 delete t; 96 setpriority(PRIO_PROCESS, 0, prio); 97 pthread_once(&gDoSchedulingGroupOnce, checkDoSchedulingGroup); 98 if (gDoSchedulingGroup) { 99 if (prio >= ANDROID_PRIORITY_BACKGROUND) { 100 set_sched_policy(androidGetTid(), SP_BACKGROUND); 101 } else { 102 set_sched_policy(androidGetTid(), SP_FOREGROUND); 103 } 104 } 105 106 if (name) { 107 #if defined(HAVE_PRCTL) 108 // Mac OS doesn't have this, and we build libutil for the host too 109 int hasAt = 0; 110 int hasDot = 0; 111 char *s = name; 112 while (*s) { 113 if (*s == '.') hasDot = 1; 114 else if (*s == '@') hasAt = 1; 115 s++; 116 } 117 int len = s - name; 118 if (len < 15 || hasAt || !hasDot) { 119 s = name; 120 } else { 121 s = name + len - 15; 122 } 123 prctl(PR_SET_NAME, (unsigned long) s, 0, 0, 0); 124 #endif 125 free(name); 126 } 127 return f(u); 128 } 129 }; 130 131 int androidCreateRawThreadEtc(android_thread_func_t entryFunction, 132 void *userData, 133 const char* threadName, 134 int32_t threadPriority, 135 size_t threadStackSize, 136 android_thread_id_t *threadId) 137 { 138 pthread_attr_t attr; 139 pthread_attr_init(&attr); 140 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 141 142 #ifdef HAVE_ANDROID_OS /** valgrind is rejecting RT-priority create reqs */ 143 if (threadPriority != PRIORITY_DEFAULT || threadName != NULL) { 144 // We could avoid the trampoline if there was a way to get to the 145 // android_thread_id_t (pid) from pthread_t 146 thread_data_t* t = new thread_data_t; 147 t->priority = threadPriority; 148 t->threadName = threadName ? strdup(threadName) : NULL; 149 t->entryFunction = entryFunction; 150 t->userData = userData; 151 entryFunction = (android_thread_func_t)&thread_data_t::trampoline; 152 userData = t; 153 } 154 #endif 155 156 if (threadStackSize) { 157 pthread_attr_setstacksize(&attr, threadStackSize); 158 } 159 160 errno = 0; 161 pthread_t thread; 162 int result = pthread_create(&thread, &attr, 163 (android_pthread_entry)entryFunction, userData); 164 pthread_attr_destroy(&attr); 165 if (result != 0) { 166 LOGE("androidCreateRawThreadEtc failed (entry=%p, res=%d, errno=%d)\n" 167 "(android threadPriority=%d)", 168 entryFunction, result, errno, threadPriority); 169 return 0; 170 } 171 172 // Note that *threadID is directly available to the parent only, as it is 173 // assigned after the child starts. Use memory barrier / lock if the child 174 // or other threads also need access. 175 if (threadId != NULL) { 176 *threadId = (android_thread_id_t)thread; // XXX: this is not portable 177 } 178 return 1; 179 } 180 181 android_thread_id_t androidGetThreadId() 182 { 183 return (android_thread_id_t)pthread_self(); 184 } 185 186 // ---------------------------------------------------------------------------- 187 #elif defined(HAVE_WIN32_THREADS) 188 // ---------------------------------------------------------------------------- 189 190 /** 191 * Trampoline to make us __stdcall-compliant. 192 * 193 * We're expected to delete "vDetails" when we're done. 194 */ 195 struct threadDetails { 196 int (*func)(void*); 197 void* arg; 198 }; 199 static __stdcall unsigned int threadIntermediary(void* vDetails) 200 { 201 struct threadDetails* pDetails = (struct threadDetails*) vDetails; 202 int result; 203 204 result = (*(pDetails->func))(pDetails->arg); 205 206 delete pDetails; 207 208 LOG(LOG_VERBOSE, "thread", "thread exiting\n"); 209 return (unsigned int) result; 210 } 211 212 /** 213 * Create and run a new thread. 214 */ 215 static bool doCreateThread(android_thread_func_t fn, void* arg, android_thread_id_t *id) 216 { 217 HANDLE hThread; 218 struct threadDetails* pDetails = new threadDetails; // must be on heap 219 unsigned int thrdaddr; 220 221 pDetails->func = fn; 222 pDetails->arg = arg; 223 224 #if defined(HAVE__BEGINTHREADEX) 225 hThread = (HANDLE) _beginthreadex(NULL, 0, threadIntermediary, pDetails, 0, 226 &thrdaddr); 227 if (hThread == 0) 228 #elif defined(HAVE_CREATETHREAD) 229 hThread = CreateThread(NULL, 0, 230 (LPTHREAD_START_ROUTINE) threadIntermediary, 231 (void*) pDetails, 0, (DWORD*) &thrdaddr); 232 if (hThread == NULL) 233 #endif 234 { 235 LOG(LOG_WARN, "thread", "WARNING: thread create failed\n"); 236 return false; 237 } 238 239 #if defined(HAVE_CREATETHREAD) 240 /** close the management handle */ 241 CloseHandle(hThread); 242 #endif 243 244 if (id != NULL) { 245 *id = (android_thread_id_t)thrdaddr; 246 } 247 248 return true; 249 } 250 251 int androidCreateRawThreadEtc(android_thread_func_t fn, 252 void *userData, 253 const char* threadName, 254 int32_t threadPriority, 255 size_t threadStackSize, 256 android_thread_id_t *threadId) 257 { 258 return doCreateThread( fn, userData, threadId); 259 } 260 261 android_thread_id_t androidGetThreadId() 262 { 263 return (android_thread_id_t)GetCurrentThreadId(); 264 } 265 266 // ---------------------------------------------------------------------------- 267 #else 268 #error "Threads not supported" 269 #endif 270 271 // ---------------------------------------------------------------------------- 272 273 int androidCreateThread(android_thread_func_t fn, void* arg) 274 { 275 return createThreadEtc(fn, arg); 276 } 277 278 int androidCreateThreadGetID(android_thread_func_t fn, void *arg, android_thread_id_t *id) 279 { 280 return createThreadEtc(fn, arg, "android:unnamed_thread", 281 PRIORITY_DEFAULT, 0, id); 282 } 283 284 static android_create_thread_fn gCreateThreadFn = androidCreateRawThreadEtc; 285 286 int androidCreateThreadEtc(android_thread_func_t entryFunction, 287 void *userData, 288 const char* threadName, 289 int32_t threadPriority, 290 size_t threadStackSize, 291 android_thread_id_t *threadId) 292 { 293 return gCreateThreadFn(entryFunction, userData, threadName, 294 threadPriority, threadStackSize, threadId); 295 } 296 297 void androidSetCreateThreadFunc(android_create_thread_fn func) 298 { 299 gCreateThreadFn = func; 300 } 301 302 pid_t androidGetTid() 303 { 304 #ifdef HAVE_GETTID 305 return gettid(); 306 #else 307 return getpid(); 308 #endif 309 } 310 311 int androidSetThreadSchedulingGroup(pid_t tid, int grp) 312 { 313 if (grp > ANDROID_TGROUP_MAX || grp < 0) { 314 return BAD_VALUE; 315 } 316 317 #if defined(HAVE_PTHREADS) 318 pthread_once(&gDoSchedulingGroupOnce, checkDoSchedulingGroup); 319 if (gDoSchedulingGroup) { 320 // set_sched_policy does not support tid == 0 321 if (tid == 0) { 322 tid = androidGetTid(); 323 } 324 if (set_sched_policy(tid, (grp == ANDROID_TGROUP_BG_NONINTERACT) ? 325 SP_BACKGROUND : SP_FOREGROUND)) { 326 return PERMISSION_DENIED; 327 } 328 } 329 #endif 330 331 return NO_ERROR; 332 } 333 334 int androidSetThreadPriority(pid_t tid, int pri) 335 { 336 int rc = 0; 337 338 #if defined(HAVE_PTHREADS) 339 int lasterr = 0; 340 341 pthread_once(&gDoSchedulingGroupOnce, checkDoSchedulingGroup); 342 if (gDoSchedulingGroup) { 343 // set_sched_policy does not support tid == 0 344 int policy_tid; 345 if (tid == 0) { 346 policy_tid = androidGetTid(); 347 } else { 348 policy_tid = tid; 349 } 350 if (pri >= ANDROID_PRIORITY_BACKGROUND) { 351 rc = set_sched_policy(policy_tid, SP_BACKGROUND); 352 } else if (getpriority(PRIO_PROCESS, tid) >= ANDROID_PRIORITY_BACKGROUND) { 353 rc = set_sched_policy(policy_tid, SP_FOREGROUND); 354 } 355 } 356 357 if (rc) { 358 lasterr = errno; 359 } 360 361 if (setpriority(PRIO_PROCESS, tid, pri) < 0) { 362 rc = INVALID_OPERATION; 363 } else { 364 errno = lasterr; 365 } 366 #endif 367 368 return rc; 369 } 370 371 int androidGetThreadPriority(pid_t tid) { 372 #if defined(HAVE_PTHREADS) 373 return getpriority(PRIO_PROCESS, tid); 374 #else 375 return ANDROID_PRIORITY_NORMAL; 376 #endif 377 } 378 379 int androidGetThreadSchedulingGroup(pid_t tid) 380 { 381 int ret = ANDROID_TGROUP_DEFAULT; 382 383 #if defined(HAVE_PTHREADS) 384 // convention is to not call get/set_sched_policy methods if disabled by property 385 pthread_once(&gDoSchedulingGroupOnce, checkDoSchedulingGroup); 386 if (gDoSchedulingGroup) { 387 SchedPolicy policy; 388 // get_sched_policy does not support tid == 0 389 if (tid == 0) { 390 tid = androidGetTid(); 391 } 392 if (get_sched_policy(tid, &policy) < 0) { 393 ret = INVALID_OPERATION; 394 } else { 395 switch (policy) { 396 case SP_BACKGROUND: 397 ret = ANDROID_TGROUP_BG_NONINTERACT; 398 break; 399 case SP_FOREGROUND: 400 ret = ANDROID_TGROUP_FG_BOOST; 401 break; 402 default: 403 // should not happen, as enum SchedPolicy does not have any other values 404 ret = INVALID_OPERATION; 405 break; 406 } 407 } 408 } 409 #endif 410 411 return ret; 412 } 413 414 namespace android { 415 416 /** 417 * =========================================================================== 418 * Mutex class 419 * =========================================================================== 420 */ 421 422 #if defined(HAVE_PTHREADS) 423 // implemented as inlines in threads.h 424 #elif defined(HAVE_WIN32_THREADS) 425 426 Mutex::Mutex() 427 { 428 HANDLE hMutex; 429 430 assert(sizeof(hMutex) == sizeof(mState)); 431 432 hMutex = CreateMutex(NULL, FALSE, NULL); 433 mState = (void*) hMutex; 434 } 435 436 Mutex::Mutex(const char* name) 437 { 438 // XXX: name not used for now 439 HANDLE hMutex; 440 441 assert(sizeof(hMutex) == sizeof(mState)); 442 443 hMutex = CreateMutex(NULL, FALSE, NULL); 444 mState = (void*) hMutex; 445 } 446 447 Mutex::Mutex(int type, const char* name) 448 { 449 // XXX: type and name not used for now 450 HANDLE hMutex; 451 452 assert(sizeof(hMutex) == sizeof(mState)); 453 454 hMutex = CreateMutex(NULL, FALSE, NULL); 455 mState = (void*) hMutex; 456 } 457 458 Mutex::~Mutex() 459 { 460 CloseHandle((HANDLE) mState); 461 } 462 463 status_t Mutex::lock() 464 { 465 DWORD dwWaitResult; 466 dwWaitResult = WaitForSingleObject((HANDLE) mState, INFINITE); 467 return dwWaitResult != WAIT_OBJECT_0 ? -1 : NO_ERROR; 468 } 469 470 void Mutex::unlock() 471 { 472 if (!ReleaseMutex((HANDLE) mState)) 473 LOG(LOG_WARN, "thread", "WARNING: bad result from unlocking mutex\n"); 474 } 475 476 status_t Mutex::tryLock() 477 { 478 DWORD dwWaitResult; 479 480 dwWaitResult = WaitForSingleObject((HANDLE) mState, 0); 481 if (dwWaitResult != WAIT_OBJECT_0 && dwWaitResult != WAIT_TIMEOUT) 482 LOG(LOG_WARN, "thread", "WARNING: bad result from try-locking mutex\n"); 483 return (dwWaitResult == WAIT_OBJECT_0) ? 0 : -1; 484 } 485 486 #else 487 #error "Somebody forgot to implement threads for this platform." 488 #endif 489 490 491 /** 492 * =========================================================================== 493 * Condition class 494 * =========================================================================== 495 */ 496 497 #if defined(HAVE_PTHREADS) 498 // implemented as inlines in threads.h 499 #elif defined(HAVE_WIN32_THREADS) 500 501 /** 502 * Windows doesn't have a condition variable solution. It's possible 503 * to create one, but it's easy to get it wrong. For a discussion, and 504 * the origin of this implementation, see: 505 * 506 * http://www.cs.wustl.edu/~schmidt/win32-cv-1.html 507 * 508 * The implementation shown on the page does NOT follow POSIX semantics. 509 * As an optimization they require acquiring the external mutex before 510 * calling signal() and broadcast(), whereas POSIX only requires grabbing 511 * it before calling wait(). The implementation here has been un-optimized 512 * to have the correct behavior. 513 */ 514 typedef struct WinCondition { 515 // Number of waiting threads. 516 int waitersCount; 517 518 // Serialize access to waitersCount. 519 CRITICAL_SECTION waitersCountLock; 520 521 // Semaphore used to queue up threads waiting for the condition to 522 // become signaled. 523 HANDLE sema; 524 525 // An auto-reset event used by the broadcast/signal thread to wait 526 // for all the waiting thread(s) to wake up and be released from 527 // the semaphore. 528 HANDLE waitersDone; 529 530 // This mutex wouldn't be necessary if we required that the caller 531 // lock the external mutex before calling signal() and broadcast(). 532 // I'm trying to mimic pthread semantics though. 533 HANDLE internalMutex; 534 535 // Keeps track of whether we were broadcasting or signaling. This 536 // allows us to optimize the code if we're just signaling. 537 bool wasBroadcast; 538 539 status_t wait(WinCondition* condState, HANDLE hMutex, nsecs_t* abstime) 540 { 541 // Increment the wait count, avoiding race conditions. 542 EnterCriticalSection(&condState->waitersCountLock); 543 condState->waitersCount++; 544 //printf("+++ wait: incr waitersCount to %d (tid=%ld)\n", 545 // condState->waitersCount, getThreadId()); 546 LeaveCriticalSection(&condState->waitersCountLock); 547 548 DWORD timeout = INFINITE; 549 if (abstime) { 550 nsecs_t reltime = *abstime - systemTime(); 551 if (reltime < 0) 552 reltime = 0; 553 timeout = reltime/1000000; 554 } 555 556 // Atomically release the external mutex and wait on the semaphore. 557 DWORD res = 558 SignalObjectAndWait(hMutex, condState->sema, timeout, FALSE); 559 560 //printf("+++ wait: awake (tid=%ld)\n", getThreadId()); 561 562 // Reacquire lock to avoid race conditions. 563 EnterCriticalSection(&condState->waitersCountLock); 564 565 // No longer waiting. 566 condState->waitersCount--; 567 568 // Check to see if we're the last waiter after a broadcast. 569 bool lastWaiter = (condState->wasBroadcast && condState->waitersCount == 0); 570 571 //printf("+++ wait: lastWaiter=%d (wasBc=%d wc=%d)\n", 572 // lastWaiter, condState->wasBroadcast, condState->waitersCount); 573 574 LeaveCriticalSection(&condState->waitersCountLock); 575 576 // If we're the last waiter thread during this particular broadcast 577 // then signal broadcast() that we're all awake. It'll drop the 578 // internal mutex. 579 if (lastWaiter) { 580 // Atomically signal the "waitersDone" event and wait until we 581 // can acquire the internal mutex. We want to do this in one step 582 // because it ensures that everybody is in the mutex FIFO before 583 // any thread has a chance to run. Without it, another thread 584 // could wake up, do work, and hop back in ahead of us. 585 SignalObjectAndWait(condState->waitersDone, condState->internalMutex, 586 INFINITE, FALSE); 587 } else { 588 // Grab the internal mutex. 589 WaitForSingleObject(condState->internalMutex, INFINITE); 590 } 591 592 // Release the internal and grab the external. 593 ReleaseMutex(condState->internalMutex); 594 WaitForSingleObject(hMutex, INFINITE); 595 596 return res == WAIT_OBJECT_0 ? NO_ERROR : -1; 597 } 598 } WinCondition; 599 600 /** 601 * Constructor. Set up the WinCondition stuff. 602 */ 603 Condition::Condition() 604 { 605 WinCondition* condState = new WinCondition; 606 607 condState->waitersCount = 0; 608 condState->wasBroadcast = false; 609 // semaphore: no security, initial value of 0 610 condState->sema = CreateSemaphore(NULL, 0, 0x7fffffff, NULL); 611 InitializeCriticalSection(&condState->waitersCountLock); 612 // auto-reset event, not signaled initially 613 condState->waitersDone = CreateEvent(NULL, FALSE, FALSE, NULL); 614 // used so we don't have to lock external mutex on signal/broadcast 615 condState->internalMutex = CreateMutex(NULL, FALSE, NULL); 616 617 mState = condState; 618 } 619 620 /** 621 * Destructor. Free Windows resources as well as our allocated storage. 622 */ 623 Condition::~Condition() 624 { 625 WinCondition* condState = (WinCondition*) mState; 626 if (condState != NULL) { 627 CloseHandle(condState->sema); 628 CloseHandle(condState->waitersDone); 629 delete condState; 630 } 631 } 632 633 634 status_t Condition::wait(Mutex& mutex) 635 { 636 WinCondition* condState = (WinCondition*) mState; 637 HANDLE hMutex = (HANDLE) mutex.mState; 638 639 return ((WinCondition*)mState)->wait(condState, hMutex, NULL); 640 } 641 642 status_t Condition::waitRelative(Mutex& mutex, nsecs_t reltime) 643 { 644 WinCondition* condState = (WinCondition*) mState; 645 HANDLE hMutex = (HANDLE) mutex.mState; 646 nsecs_t absTime = systemTime()+reltime; 647 648 return ((WinCondition*)mState)->wait(condState, hMutex, &absTime); 649 } 650 651 /** 652 * Signal the condition variable, allowing one thread to continue. 653 */ 654 void Condition::signal() 655 { 656 WinCondition* condState = (WinCondition*) mState; 657 658 // Lock the internal mutex. This ensures that we don't clash with 659 // broadcast(). 660 WaitForSingleObject(condState->internalMutex, INFINITE); 661 662 EnterCriticalSection(&condState->waitersCountLock); 663 bool haveWaiters = (condState->waitersCount > 0); 664 LeaveCriticalSection(&condState->waitersCountLock); 665 666 // If no waiters, then this is a no-op. Otherwise, knock the semaphore 667 // down a notch. 668 if (haveWaiters) 669 ReleaseSemaphore(condState->sema, 1, 0); 670 671 // Release internal mutex. 672 ReleaseMutex(condState->internalMutex); 673 } 674 675 /** 676 * Signal the condition variable, allowing all threads to continue. 677 * 678 * First we have to wake up all threads waiting on the semaphore, then 679 * we wait until all of the threads have actually been woken before 680 * releasing the internal mutex. This ensures that all threads are woken. 681 */ 682 void Condition::broadcast() 683 { 684 WinCondition* condState = (WinCondition*) mState; 685 686 // Lock the internal mutex. This keeps the guys we're waking up 687 // from getting too far. 688 WaitForSingleObject(condState->internalMutex, INFINITE); 689 690 EnterCriticalSection(&condState->waitersCountLock); 691 bool haveWaiters = false; 692 693 if (condState->waitersCount > 0) { 694 haveWaiters = true; 695 condState->wasBroadcast = true; 696 } 697 698 if (haveWaiters) { 699 // Wake up all the waiters. 700 ReleaseSemaphore(condState->sema, condState->waitersCount, 0); 701 702 LeaveCriticalSection(&condState->waitersCountLock); 703 704 // Wait for all awakened threads to acquire the counting semaphore. 705 // The last guy who was waiting sets this. 706 WaitForSingleObject(condState->waitersDone, INFINITE); 707 708 // Reset wasBroadcast. (No crit section needed because nobody 709 // else can wake up to poke at it.) 710 condState->wasBroadcast = 0; 711 } else { 712 // nothing to do 713 LeaveCriticalSection(&condState->waitersCountLock); 714 } 715 716 // Release internal mutex. 717 ReleaseMutex(condState->internalMutex); 718 } 719 720 #else 721 #error "condition variables not supported on this platform" 722 #endif 723 724 // ---------------------------------------------------------------------------- 725 726 /** 727 * This is our thread object! 728 */ 729 730 Thread::Thread(bool canCallJava) 731 : mCanCallJava(canCallJava), 732 mThread(thread_id_t(-1)), 733 mLock("Thread::mLock"), 734 mStatus(NO_ERROR), 735 mExitPending(false), mRunning(false) 736 #ifdef HAVE_ANDROID_OS 737 , mTid(-1) 738 #endif 739 { 740 } 741 742 Thread::~Thread() 743 { 744 } 745 746 status_t Thread::readyToRun() 747 { 748 return NO_ERROR; 749 } 750 751 status_t Thread::run(const char* name, int32_t priority, size_t stack) 752 { 753 Mutex::Autolock _l(mLock); 754 755 if (mRunning) { 756 // thread already started 757 return INVALID_OPERATION; 758 } 759 760 // reset status and exitPending to their default value, so we can 761 // try again after an error happened (either below, or in readyToRun()) 762 mStatus = NO_ERROR; 763 mExitPending = false; 764 mThread = thread_id_t(-1); 765 766 // hold a strong reference on ourself 767 mHoldSelf = this; 768 769 mRunning = true; 770 771 bool res; 772 if (mCanCallJava) { 773 res = createThreadEtc(_threadLoop, 774 this, name, priority, stack, &mThread); 775 } else { 776 res = androidCreateRawThreadEtc(_threadLoop, 777 this, name, priority, stack, &mThread); 778 } 779 780 if (res == false) { 781 mStatus = UNKNOWN_ERROR; // something happened! 782 mRunning = false; 783 mThread = thread_id_t(-1); 784 mHoldSelf.clear(); // "this" may have gone away after this. 785 786 return UNKNOWN_ERROR; 787 } 788 789 // Do not refer to mStatus here: The thread is already running (may, in fact 790 // already have exited with a valid mStatus result). The NO_ERROR indication 791 // here merely indicates successfully starting the thread and does not 792 // imply successful termination/execution. 793 return NO_ERROR; 794 795 // Exiting scope of mLock is a memory barrier and allows new thread to run 796 } 797 798 int Thread::_threadLoop(void* user) 799 { 800 Thread* const self = static_cast<Thread*>(user); 801 802 sp<Thread> strong(self->mHoldSelf); 803 wp<Thread> weak(strong); 804 self->mHoldSelf.clear(); 805 806 #ifdef HAVE_ANDROID_OS 807 // this is very useful for debugging with gdb 808 self->mTid = gettid(); 809 #endif 810 811 bool first = true; 812 813 do { 814 bool result; 815 if (first) { 816 first = false; 817 self->mStatus = self->readyToRun(); 818 result = (self->mStatus == NO_ERROR); 819 820 if (result && !self->exitPending()) { 821 // Binder threads (and maybe others) rely on threadLoop 822 // running at least once after a successful ::readyToRun() 823 // (unless, of course, the thread has already been asked to exit 824 // at that point). 825 // This is because threads are essentially used like this: 826 // (new ThreadSubclass())->run(); 827 // The caller therefore does not retain a strong reference to 828 // the thread and the thread would simply disappear after the 829 // successful ::readyToRun() call instead of entering the 830 // threadLoop at least once. 831 result = self->threadLoop(); 832 } 833 } else { 834 result = self->threadLoop(); 835 } 836 837 // establish a scope for mLock 838 { 839 Mutex::Autolock _l(self->mLock); 840 if (result == false || self->mExitPending) { 841 self->mExitPending = true; 842 self->mRunning = false; 843 // clear thread ID so that requestExitAndWait() does not exit if 844 // called by a new thread using the same thread ID as this one. 845 self->mThread = thread_id_t(-1); 846 // note that interested observers blocked in requestExitAndWait are 847 // awoken by broadcast, but blocked on mLock until break exits scope 848 self->mThreadExitedCondition.broadcast(); 849 break; 850 } 851 } 852 853 // Release our strong reference, to let a chance to the thread 854 // to die a peaceful death. 855 strong.clear(); 856 // And immediately, re-acquire a strong reference for the next loop 857 strong = weak.promote(); 858 } while(strong != 0); 859 860 return 0; 861 } 862 863 void Thread::requestExit() 864 { 865 Mutex::Autolock _l(mLock); 866 mExitPending = true; 867 } 868 869 status_t Thread::requestExitAndWait() 870 { 871 Mutex::Autolock _l(mLock); 872 if (mThread == getThreadId()) { 873 LOGW( 874 "Thread (this=%p): don't call waitForExit() from this " 875 "Thread object's thread. It's a guaranteed deadlock!", 876 this); 877 878 return WOULD_BLOCK; 879 } 880 881 mExitPending = true; 882 883 while (mRunning == true) { 884 mThreadExitedCondition.wait(mLock); 885 } 886 // This next line is probably not needed any more, but is being left for 887 // historical reference. Note that each interested party will clear flag. 888 mExitPending = false; 889 890 return mStatus; 891 } 892 893 status_t Thread::join() 894 { 895 Mutex::Autolock _l(mLock); 896 if (mThread == getThreadId()) { 897 LOGW( 898 "Thread (this=%p): don't call join() from this " 899 "Thread object's thread. It's a guaranteed deadlock!", 900 this); 901 902 return WOULD_BLOCK; 903 } 904 905 while (mRunning == true) { 906 mThreadExitedCondition.wait(mLock); 907 } 908 909 return mStatus; 910 } 911 912 bool Thread::exitPending() const 913 { 914 Mutex::Autolock _l(mLock); 915 return mExitPending; 916 } 917 918 919 920 }; // namespace android
- The definition of Mutex in thread
-
1 class Mutex { 2 public: 3 enum { 4 PRIVATE = 0, 5 SHARED = 1 6 }; 7 Mutex(); 8 Mutex(const char* name); 9 Mutex(int type, const char* name = NULL); 10 ~Mutex(); 11 status_t lock(); 12 void unlock(); 13 status_t tryLock(); 14 class Autolock { 15 public: 16 inline Autolock(Mutex& mutex) : mLock(mutex) { mLock.lock(); } 17 inline Autolock(Mutex* mutex) : mLock(*mutex) { mLock.lock(); } 18 inline ~Autolock() { mLock.unlock(); } 19 private: 20 Mutex& mLock; 21 }; 22 private: 23 friend class Condition; 24 // A mutex cannot be copied 25 Mutex(const Mutex&); 26 Mutex& operator = (const Mutex&); 27 #if defined(HAVE_PTHREADS) 28 pthread_mutex_t mMutex; 29 #else 30 void _init(); 31 void* mState; 32 #endif 33 }; 34 #if defined(HAVE_PTHREADS) 35 inline Mutex::Mutex() { 36 pthread_mutex_init(&mMutex, NULL); 37 } 38 inline Mutex::Mutex(const char* name) { 39 pthread_mutex_init(&mMutex, NULL); 40 } 41 inline Mutex::Mutex(int type, const char* name) { 42 if (type == SHARED) { 43 pthread_mutexattr_t attr; 44 pthread_mutexattr_init(&attr); 45 pthread_mutexattr_setpshared(&attr, PTHREAD_PROCESS_SHARED); 46 pthread_mutex_init(&mMutex, &attr); 47 pthread_mutexattr_destroy(&attr); 48 } else { 49 pthread_mutex_init(&mMutex, NULL); 50 } 51 } 52 inline Mutex::~Mutex() { 53 pthread_mutex_destroy(&mMutex); 54 } 55 inline status_t Mutex::lock() { 56 return -pthread_mutex_lock(&mMutex); 57 } 58 inline void Mutex::unlock() { 59 pthread_mutex_unlock(&mMutex); 60 } 61 inline status_t Mutex::tryLock() { 62 return -pthread_mutex_trylock(&mMutex); 63 } 64 #endif // HAVE_PTHREADS 65 typedef Mutex::Autolock AutoMutex;
- The interface of thread
-
1 lass Thread : virtual public RefBase 2 { 3 public: 4 Thread(bool canCallJava = true); 5 virtual ~Thread(); 6 virtual status_t run(const char* name = 0, 7 int32_t priority = PRIORITY_DEFAULT, 8 size_t stack = 0); 9 virtual void requestExit();ns 10 virtual status_t readyToRun(); 11 status_t requestExitAndWait(); 12 status_t join(); 13 protected: 14 bool exitPending() const; 15 private: 16 virtual bool threadLoop() = 0; 17 private: 18 Thread& operator=(const Thread&); 19 static int _threadLoop(void* user); 20 const bool mCanCallJava; 21 thread_id_t mThread; 22 mutable Mutex mLock; 23 Condition mThreadExitedCondition; 24 status_t mStatus; 25 volatile bool mExitPending; 26 volatile bool mRunning; 27 sp<Thread> mHoldSelf; 28 #if HAVE_ANDROID_OS 29 int mTid; 30 #endif 31 };
- Create a thread on linux as global function
-
1 inline bool createThread(thread_func_t f, void *a) { 2 return androidCreateThread(f, a) ? true : false; 3 } 4 int androidCreateThread(android_thread_func_t fn, void* arg) 5 { 6 return createThreadEtc(fn, arg); 7 } 8 9 // Create thread with lots of parameters 10 inline bool createThreadEtc(thread_func_t entryFunction, 11 void *userData, 12 const char* threadName = "android:unnamed_thread", 13 int32_t threadPriority = PRIORITY_DEFAULT, 14 size_t threadStackSize = 0, 15 thread_id_t *threadId = 0) 16 { 17 return androidCreateThreadEtc(entryFunction, userData, threadName, 18 threadPriority, threadStackSize, threadId) ? true : false; 19 } 20 static android_create_thread_fn gCreateThreadFn = androidCreateRawThreadEtc; 21 int androidCreateRawThreadEtc(android_thread_func_t entryFunction, 22 void *userData, 23 const char* threadName, 24 int32_t threadPriority, 25 size_t threadStackSize, 26 android_thread_id_t *threadId) 27 { 28 pthread_attr_t attr; 29 pthread_attr_init(&attr); 30 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); 31 #ifdef HAVE_ANDROID_OS /** valgrind is rejecting RT-priority create reqs */ 32 if (threadPriority != PRIORITY_DEFAULT || threadName != NULL) { 33 // We could avoid the trampoline if there was a way to get to the 34 // android_thread_id_t (pid) from pthread_t 35 thread_data_t* t = new thread_data_t; 36 t->priority = threadPriority; 37 t->threadName = threadName ? strdup(threadName) : NULL; 38 t->entryFunction = entryFunction; 39 t->userData = userData; 40 entryFunction = (android_thread_func_t)&thread_data_t::trampoline; 41 userData = t; 42 } 43 #endif 44 if (threadStackSize) { 45 pthread_attr_setstacksize(&attr, threadStackSize); 46 } 47 errno = 0; 48 pthread_t thread; 49 int result = pthread_create(&thread, &attr,android_pthread_entry)entryFunction, userData); 50 pthread_attr_destroy(&attr); 51 if (result != 0) { 52 LOGE("androidCreateRawThreadEtc failed (entry=%p, res=%d, errno=%d)\n" 53 "(android threadPriority=%d)", 54 entryFunction, result, errno, threadPriority); 55 return 0; 56 } 57 // Note that *threadID is directly available to the parent only, as it is 58 // assigned after the child starts. Use memory barrier / lock if the child 59 // or other threads also need access. 60 if (threadId != NULL) { 61 *threadId = (android_thread_id_t)thread; // XXX: this is not portable 62 } 63 return 1; 64 }
- Create a new thread on win32 as global function
-
1 int androidCreateRawThreadEtc(android_thread_func_t fn, 2 void *userData, 3 const char* threadName, 4 int32_t threadPriority, 5 size_t threadStackSize, 6 android_thread_id_t *threadId) 7 { 8 return doCreateThread( fn, userData, threadId); 9 } 10 static bool doCreateThread(android_thread_func_t fn, void* arg, android_thread_id_t *id) 11 { 12 HANDLE hThread; 13 struct threadDetails* pDetails = new threadDetails; // must be on heap 14 unsigned int thrdaddr; 15 pDetails->func = fn; 16 pDetails->arg = arg; 17 #if defined(HAVE__BEGINTHREADEX) 18 hThread = (HANDLE) _beginthreadex(NULL, 0, threadIntermediary, pDetails, 0,&thrdaddr); 19 if (hThread == 0) 20 #elif defined(HAVE_CREATETHREAD) 21 hThread = CreateThread(NULL, 0,LPTHREAD_START_ROUTINE) threadIntermediary, 22 (void*) pDetails, 0, (DWORD*) &thrdaddr); 23 if (hThread == NULL) 24 #endif 25 { 26 LOG(LOG_WARN, "thread", "WARNING: thread create failed\n"); 27 return false; 28 } 29 #if defined(HAVE_CREATETHREAD) 30 /** close the management handle */ 31 CloseHandle(hThread); 32 #endif 33 if (id != NULL) { 34 *id = (android_thread_id_t)thrdaddr; 35 } 36 return true; 37 }
- Create a thead in thread object
-
1 status_t Thread::run(const char* name, int32_t priority, size_t stack) 2 { 3 Mutex::Autolock _l(mLock); 4 if (mRunning) { 5 // thread already started 6 return INVALID_OPERATION; 7 }) 8 mStatus = NO_ERROR; 9 mExitPending = false; 10 mThread = thread_id_t(-1); 11 mHoldSelf = this; 12 mRunning = true; 13 bool res; 14 if (mCanCallJava) { 15 res = createThreadEtc(_threadLoop, 16 this, name, priority, stack, &mThread); 17 } else { 18 res = androidCreateRawThreadEtc(_threadLoop, 19 this, name, priority, stack, &mThread); 20 } 21 if (res == false) { 22 mStatus = UNKNOWN_ERROR; // something happened! 23 mRunning = false; 24 mThread = thread_id_t(-1); 25 mHoldSelf.clear(); // "this" may have gone away after this. 26 27 return UNKNOWN_ERROR; 28 } 29 return NO_ERROR; 30 } 31 int Thread::_threadLoop(void* user) 32 { 33 Thread* const self = static_cast<Thread*>(user); 34 sp<Thread> strong(self->mHoldSelf); 35 wp<Thread> weak(strong); 36 self->mHoldSelf.clear(); 37 #ifdef HAVE_ANDROID_OS 38 // this is very useful for debugging with gdb 39 self->mTid = gettid(); 40 #endif 41 bool first = true; 42 43 do { 44 bool result; 45 if (first) { 46 first = false; 47 self->mStatus = self->readyToRun(); 48 result = (self->mStatus == NO_ERROR); 49 50 if (result && !self->exitPending()) { 51 result = self->threadLoop(); 52 } 53 } else { 54 result = self->threadLoop(); 55 } 56 // establish a scope for mLock 57 { 58 Mutex::Autolock _l(self->mLock); 59 if (result == false || self->mExitPending) { 60 self->mExitPending = true; 61 self->mRunning = false; 62 // clear thread ID so that requestExitAndWait() does not exit if 63 // called by a new thread using the same thread ID as this one. 64 self->mThread = thread_id_t(-1); 65 // note that interested observers blocked in requestExitAndWait are 66 // awoken by broadcast, but blocked on mLock until break exits scope 67 self->mThreadExitedCondition.broadcast(); 68 break; 69 } 70 } 71 strong.clear(); 72 strong = weak.promote(); 73 } while(strong != 0); 74 return 0; 75 }
ProcessState
- ProcessState.h
-
1 /** 2 * Copyright (C) 2005 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ANDROID_PROCESS_STATE_H 18 #define ANDROID_PROCESS_STATE_H 19 20 #include <binder/IBinder.h> 21 #include <utils/KeyedVector.h> 22 #include <utils/String8.h> 23 #include <utils/String16.h> 24 25 #include <utils/threads.h> 26 27 // --------------------------------------------------------------------------- 28 namespace android { 29 30 // Global variables 31 extern int mArgC; 32 extern const char* const* mArgV; 33 extern int mArgLen; 34 35 class IPCThreadState; 36 37 class ProcessState : public virtual RefBase 38 { 39 public: 40 static sp<ProcessState> self(); 41 void setContextObject(const sp<IBinder>& object); 42 sp<IBinder> getContextObject(const sp<IBinder>& caller); 43 void setContextObject(const sp<IBinder>& object, 44 const String16& name); 45 sp<IBinder> getContextObject(const String16& name, 46 const sp<IBinder>& caller); 47 48 void startThreadPool(); 49 typedef bool (*context_check_func)(const String16& name, 50 const sp<IBinder>& caller, 51 void* userData); 52 53 bool isContextManager(void) const; 54 bool becomeContextManager( 55 context_check_func checkFunc, 56 void* userData); 57 58 sp<IBinder> getStrongProxyForHandle(int32_t handle); 59 wp<IBinder> getWeakProxyForHandle(int32_t handle); 60 void expungeHandle(int32_t handle, IBinder* binder); 61 62 void setArgs(int argc, const char* const argv[]); 63 int getArgC() const; 64 const char* const* getArgV() const; 65 66 void setArgV0(const char* txt); 67 68 void spawnPooledThread(bool isMain); 69 70 private: 71 friend class IPCThreadState; 72 73 ProcessState(); 74 ~ProcessState(); 75 76 ProcessState(const ProcessState& o); 77 ProcessState& operator=(const ProcessState& o); 78 79 struct handle_entry { 80 IBinder* binder; 81 RefBase::weakref_type* refs; 82 }; 83 84 handle_entry* lookupHandleLocked(int32_t handle); 85 86 int mDriverFD; 87 void* mVMStart; 88 89 mutable Mutex mLock; // protects everything below. 90 91 Vector<handle_entry>mHandleToObject; 92 93 bool mManagesContexts; 94 context_check_func mBinderContextCheckFunc; 95 void* mBinderContextUserData; 96 97 KeyedVector<String16, sp<IBinder> > 98 mContexts; 99 100 101 String8 mRootDir; 102 bool mThreadPoolStarted; 103 volatile int32_t mThreadPoolSeq; 104 }; 105 106 }; // namespace android 107 108 // --------------------------------------------------------------------------- 109 110 #endif // ANDROID_PROCESS_STATE_H
- ProcessState.cpp
-
1 /** 2 * Copyright (C) 2005 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #define LOG_TAG "ProcessState" 18 19 #include <cutils/process_name.h> 20 21 #include <binder/ProcessState.h> 22 23 #include <utils/Atomic.h> 24 #include <binder/BpBinder.h> 25 #include <binder/IPCThreadState.h> 26 #include <utils/Log.h> 27 #include <utils/String8.h> 28 #include <binder/IServiceManager.h> 29 #include <utils/String8.h> 30 #include <utils/threads.h> 31 32 #include <private/binder/binder_module.h> 33 #include <private/binder/Static.h> 34 35 #include <errno.h> 36 #include <fcntl.h> 37 #include <stdio.h> 38 #include <stdlib.h> 39 #include <unistd.h> 40 #include <sys/ioctl.h> 41 #include <sys/mman.h> 42 #include <sys/stat.h> 43 44 #define BINDER_VM_SIZE ((1*1024*1024) - (4096 *2)) 45 46 47 // --------------------------------------------------------------------------- 48 49 namespace android { 50 51 // Global variables 52 int mArgC; 53 const char* const* mArgV; 54 int mArgLen; 55 56 class PoolThread : public Thread 57 { 58 public: 59 PoolThread(bool isMain) 60 : mIsMain(isMain) 61 { 62 } 63 64 protected: 65 virtual bool threadLoop() 66 { 67 IPCThreadState::self()->joinThreadPool(mIsMain); 68 return false; 69 } 70 const bool mIsMain; 71 }; 72 73 sp<ProcessState> ProcessState::self() 74 { 75 if (gProcess != NULL) return gProcess; 76 77 AutoMutex _l(gProcessMutex); 78 if (gProcess == NULL) gProcess = new ProcessState; 79 return gProcess; 80 } 81 82 void ProcessState::setContextObject(const sp<IBinder>& object) 83 { 84 setContextObject(object, String16("default")); 85 } 86 87 sp<IBinder> ProcessState::getContextObject(const sp<IBinder>& caller) 88 { 89 return getStrongProxyForHandle(0); 90 } 91 92 void ProcessState::setContextObject(const sp<IBinder>& object, const String16& name) 93 { 94 AutoMutex _l(mLock); 95 mContexts.add(name, object); 96 } 97 98 sp<IBinder> ProcessState::getContextObject(const String16& name, const sp<IBinder>& caller) 99 { 100 mLock.lock(); 101 sp<IBinder> object( 102 mContexts.indexOfKey(name) >= 0 ? mContexts.valueFor(name) : NULL); 103 mLock.unlock(); 104 105 //printf("Getting context object %s for %p\n", String8(name).string(), caller.get()); 106 107 if (object != NULL) return object; 108 109 // Don't attempt to retrieve contexts if we manage them 110 if (mManagesContexts) { 111 LOGE("getContextObject(%s) failed, but we manage the contexts!\n", 112 String8(name).string()); 113 return NULL; 114 } 115 116 IPCThreadState* ipc = IPCThreadState::self(); 117 { 118 Parcel data, reply; 119 // no interface token on this magic transaction 120 data.writeString16(name); 121 data.writeStrongBinder(caller); 122 status_t result = ipc->transact(0 /**magic*/, 0, data, &reply, 0); 123 if (result == NO_ERROR) { 124 object = reply.readStrongBinder(); 125 } 126 } 127 128 ipc->flushCommands(); 129 130 if (object != NULL) setContextObject(object, name); 131 return object; 132 } 133 134 void ProcessState::startThreadPool() 135 { 136 AutoMutex _l(mLock); 137 if (!mThreadPoolStarted) { 138 mThreadPoolStarted = true; 139 spawnPooledThread(true); 140 } 141 } 142 143 bool ProcessState::isContextManager(void) const 144 { 145 return mManagesContexts; 146 } 147 148 bool ProcessState::becomeContextManager(context_check_func checkFunc, void* userData) 149 { 150 if (!mManagesContexts) { 151 AutoMutex _l(mLock); 152 mBinderContextCheckFunc = checkFunc; 153 mBinderContextUserData = userData; 154 155 int dummy = 0; 156 status_t result = ioctl(mDriverFD, BINDER_SET_CONTEXT_MGR, &dummy); 157 if (result == 0) { 158 mManagesContexts = true; 159 } else if (result == -1) { 160 mBinderContextCheckFunc = NULL; 161 mBinderContextUserData = NULL; 162 LOGE("Binder ioctl to become context manager failed: %s\n", strerror(errno)); 163 } 164 } 165 return mManagesContexts; 166 } 167 168 ProcessState::handle_entry* ProcessState::lookupHandleLocked(int32_t handle) 169 { 170 const size_t N=mHandleToObject.size(); 171 if (N <= (size_t)handle) { 172 handle_entry e; 173 e.binder = NULL; 174 e.refs = NULL; 175 status_t err = mHandleToObject.insertAt(e, N, handle+1-N); 176 if (err < NO_ERROR) return NULL; 177 } 178 return &mHandleToObject.editItemAt(handle); 179 } 180 181 sp<IBinder> ProcessState::getStrongProxyForHandle(int32_t handle) 182 { 183 sp<IBinder> result; 184 185 AutoMutex _l(mLock); 186 187 handle_entry* e = lookupHandleLocked(handle); 188 189 if (e != NULL) { 190 // We need to create a new BpBinder if there isn't currently one, OR we 191 // are unable to acquire a weak reference on this current one. See comment 192 // in getWeakProxyForHandle() for more info about this. 193 IBinder* b = e->binder; 194 if (b == NULL || !e->refs->attemptIncWeak(this)) { 195 b = new BpBinder(handle); 196 e->binder = b; 197 if (b) e->refs = b->getWeakRefs(); 198 result = b; 199 } else { 200 // This little bit of nastyness is to allow us to add a primary 201 // reference to the remote proxy when this team doesn't have one 202 // but another team is sending the handle to us. 203 result.force_set(b); 204 e->refs->decWeak(this); 205 } 206 } 207 208 return result; 209 } 210 211 wp<IBinder> ProcessState::getWeakProxyForHandle(int32_t handle) 212 { 213 wp<IBinder> result; 214 215 AutoMutex _l(mLock); 216 217 handle_entry* e = lookupHandleLocked(handle); 218 219 if (e != NULL) { 220 // We need to create a new BpBinder if there isn't currently one, OR we 221 // are unable to acquire a weak reference on this current one. The 222 // attemptIncWeak() is safe because we know the BpBinder destructor will always 223 // call expungeHandle(), which acquires the same lock we are holding now. 224 // We need to do this because there is a race condition between someone 225 // releasing a reference on this BpBinder, and a new reference on its handle 226 // arriving from the driver. 227 IBinder* b = e->binder; 228 if (b == NULL || !e->refs->attemptIncWeak(this)) { 229 b = new BpBinder(handle); 230 result = b; 231 e->binder = b; 232 if (b) e->refs = b->getWeakRefs(); 233 } else { 234 result = b; 235 e->refs->decWeak(this); 236 } 237 } 238 239 return result; 240 } 241 242 void ProcessState::expungeHandle(int32_t handle, IBinder* binder) 243 { 244 AutoMutex _l(mLock); 245 246 handle_entry* e = lookupHandleLocked(handle); 247 248 // This handle may have already been replaced with a new BpBinder 249 // (if someone failed the AttemptIncWeak() above); we don't want 250 // to overwrite it. 251 if (e && e->binder == binder) e->binder = NULL; 252 } 253 254 void ProcessState::setArgs(int argc, const char* const argv[]) 255 { 256 mArgC = argc; 257 mArgV = (const char **)argv; 258 259 mArgLen = 0; 260 for (int i=0; i<argc; i++) { 261 mArgLen += strlen(argv[i]) + 1; 262 } 263 mArgLen--; 264 } 265 266 int ProcessState::getArgC() const 267 { 268 return mArgC; 269 } 270 271 const char* const* ProcessState::getArgV() const 272 { 273 return mArgV; 274 } 275 276 void ProcessState::setArgV0(const char* txt) 277 { 278 if (mArgV != NULL) { 279 strncpy((char*)mArgV[0], txt, mArgLen); 280 set_process_name(txt); 281 } 282 } 283 284 void ProcessState::spawnPooledThread(bool isMain) 285 { 286 if (mThreadPoolStarted) { 287 int32_t s = android_atomic_add(1, &mThreadPoolSeq); 288 char buf[32]; 289 sprintf(buf, "Binder Thread #%d", s); 290 LOGV("Spawning new pooled thread, name=%s\n", buf); 291 sp<Thread> t = new PoolThread(isMain); 292 t->run(buf); 293 } 294 } 295 296 static int open_driver() 297 { 298 int fd = open("/dev/binder", O_RDWR); 299 if (fd >= 0) { 300 fcntl(fd, F_SETFD, FD_CLOEXEC); 301 int vers; 302 status_t result = ioctl(fd, BINDER_VERSION, &vers); 303 if (result == -1) { 304 LOGE("Binder ioctl to obtain version failed: %s", strerror(errno)); 305 close(fd); 306 fd = -1; 307 } 308 if (result != 0 || vers != BINDER_CURRENT_PROTOCOL_VERSION) { 309 LOGE("Binder driver protocol does not match user space protocol!"); 310 close(fd); 311 fd = -1; 312 } 313 size_t maxThreads = 15; 314 result = ioctl(fd, BINDER_SET_MAX_THREADS, &maxThreads); 315 if (result == -1) { 316 LOGE("Binder ioctl to set max threads failed: %s", strerror(errno)); 317 } 318 } else { 319 LOGW("Opening '/dev/binder' failed: %s\n", strerror(errno)); 320 } 321 return fd; 322 } 323 324 ProcessState::ProcessState() 325 : mDriverFD(open_driver()) 326 , mVMStart(MAP_FAILED) 327 , mManagesContexts(false) 328 , mBinderContextCheckFunc(NULL) 329 , mBinderContextUserData(NULL) 330 , mThreadPoolStarted(false) 331 , mThreadPoolSeq(1) 332 { 333 if (mDriverFD >= 0) { 334 // XXX Ideally, there should be a specific define for whether we 335 // have mmap (or whether we could possibly have the kernel module 336 // availabla). 337 #if !defined(HAVE_WIN32_IPC) 338 // mmap the binder, providing a chunk of virtual address space to receive transactions. 339 mVMStart = mmap(0, BINDER_VM_SIZE, PROT_READ, MAP_PRIVATE | MAP_NORESERVE, mDriverFD, 0); 340 if (mVMStart == MAP_FAILED) { 341 // *sigh* 342 LOGE("Using /dev/binder failed: unable to mmap transaction memory.\n"); 343 close(mDriverFD); 344 mDriverFD = -1; 345 } 346 #else 347 mDriverFD = -1; 348 #endif 349 } 350 351 LOG_ALWAYS_FATAL_IF(mDriverFD < 0, "Binder driver could not be opened. Terminating."); 352 } 353 354 ProcessState::~ProcessState() 355 { 356 } 357 358 }; // namespace android
- Create a new object of ProcessState and assign to global sp<ProcessState> gProcess;
-
1 sp<ProcessState> ProcessState::self() 2 { 3 if (gProcess != NULL) 4 return gProcess; 5 AutoMutex _l(gProcessMutex); 6 if (gProcess == NULL) 7 gProcess = new ProcessState; 8 return gProcess; 9 }
- Open the binder to get handler of binder
-
1 static int open_driver()//every process where the service run or client run will have its own default binder's handle 2 { 3 int fd = open("/dev/binder", O_RDWR); 4 if (fd >= 0) { 5 fcntl(fd, F_SETFD, FD_CLOEXEC); 6 int vers; 7 status_t result = ioctl(fd, BINDER_VERSION, &vers); 8 if (result == -1) { 9 LOGE("Binder ioctl to obtain version failed: %s", strerror(errno)); 10 close(fd); 11 fd = -1; 12 } 13 if (result != 0 || vers != BINDER_CURRENT_PROTOCOL_VERSION) { 14 LOGE("Binder driver protocol does not match user space protocol!"); 15 close(fd); 16 fd = -1; 17 } 18 size_t maxThreads = 15; 19 result = ioctl(fd, BINDER_SET_MAX_THREADS, &maxThreads); 20 if (result == -1) { 21 LOGE("Binder ioctl to set max threads failed: %s", strerror(errno)); 22 } 23 } else { 24 LOGW("Opening '/dev/binder' failed: %s\n", strerror(errno)); 25 } 26 return fd; 27 }
-
1 ProcessState::ProcessState() 2 : mDriverFD(open_driver()) 3 , mVMStart(MAP_FAILED) 4 , mManagesContexts(false) 5 , mBinderContextCheckFunc(NULL) 6 , mBinderContextUserData(NULL) 7 , mThreadPoolStarted(false) 8 , mThreadPoolSeq(1) 9 { 10 if (mDriverFD >= 0) { 11 // XXX Ideally, there should be a specific define for whether we 12 // have mmap (or whether we could possibly have the kernel module 13 // availabla). 14 #if !defined(HAVE_WIN32_IPC) 15 // mmap the binder, providing a chunk of virtual address space to receive transactions. 16 mVMStart = mmap(0, BINDER_VM_SIZE, PROT_READ, MAP_PRIVATE | MAP_NORESERVE, mDriverFD, 0); 17 if (mVMStart == MAP_FAILED) { 18 // *sigh* 19 LOGE("Using /dev/binder failed: unable to mmap transaction memory.\n"); 20 close(mDriverFD); 21 mDriverFD = -1; 22 } 23 #else 24 mDriverFD = -1; 25 #endif 26 } 27 }
- PoolThread of ProcessState
-
1 class PoolThread : public Thread 2 { 3 public: 4 PoolThread(bool isMain) 5 : mIsMain(isMain) 6 { 7 } 8 protected: 9 virtual bool threadLoop()//override threadLoop of Thread 10 { 11IPCThreadState::self()->joinThreadPool(mIsMain); 12 return false; 13 } 14 const bool mIsMain; 15 };
- Start thread pool
-
1 void ProcessState::startThreadPool() 2 { 3 AutoMutex _l(mLock); 4 if (!mThreadPoolStarted) { 5 mThreadPoolStarted = true; 6spawnPooledThread(true); 7 } 8 } 9 void ProcessState::spawnPooledThread(bool isMain) 10 { 11 if (mThreadPoolStarted) { 12 int32_t s = android_atomic_add(1, &mThreadPoolSeq); 13 char buf[32]; 14 sprintf(buf, "Binder Thread #%d", s); 15 LOGV("Spawning new pooled thread, name=%s\n", buf); 16 sp<Thread> t = new PoolThread(isMain); 17 t->run(buf);//thread run by calling threadLoop
18 } 19 }
IPCThreadState
- IPCThreadState.h
-
1 /** 2 * Copyright (C) 2005 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ANDROID_IPC_THREAD_STATE_H 18 #define ANDROID_IPC_THREAD_STATE_H 19 20 #include <utils/Errors.h> 21 #include <binder/Parcel.h> 22 #include <binder/ProcessState.h> 23 #include <utils/Vector.h> 24 25 #ifdef HAVE_WIN32_PROC 26 typedef int uid_t; 27 #endif 28 29 // --------------------------------------------------------------------------- 30 namespace android { 31 32 class IPCThreadState 33 { 34 public: 35 static IPCThreadState* self(); 36 static IPCThreadState* selfOrNull(); // self(), but won't instantiate 37 sp<ProcessState> process(); 38 status_t clearLastError(); 39 int getCallingPid(); 40 int getCallingUid(); 41 void setStrictModePolicy(int32_t policy); 42 int32_t getStrictModePolicy() const; 43 void setLastTransactionBinderFlags(int32_t flags); 44 int32_t getLastTransactionBinderFlags() const; 45 int64_t clearCallingIdentity(); 46 void restoreCallingIdentity(int64_t token); 47 void flushCommands(); 48 void joinThreadPool(bool isMain = true); 49 void stopProcess(bool immediate = true); 50 status_t transact(int32_t handle, 51 uint32_t code, const Parcel& data, 52 Parcel* reply, uint32_t flags); 53 void incStrongHandle(int32_t handle); 54 void decStrongHandle(int32_t handle); 55 void incWeakHandle(int32_t handle); 56 void decWeakHandle(int32_t handle); 57 status_t attemptIncStrongHandle(int32_t handle); 58 static void expungeHandle(int32_t handle, IBinder* binder); 59 status_t requestDeathNotification(int32_t handle, 60 BpBinder* proxy); 61 status_t clearDeathNotification(int32_t handle, 62 BpBinder* proxy); 63 static void shutdown(); 64 static void disableBackgroundScheduling(bool disable); 65 private: 66 IPCThreadState(); 67 ~IPCThreadState(); 68 status_t sendReply(const Parcel& reply, uint32_t flags); 69 status_t waitForResponse(Parcel *reply, 70 status_t *acquireResult=NULL); 71 status_t talkWithDriver(bool doReceive=true); 72 status_t writeTransactionData(int32_t cmd, 73 uint32_t binderFlags, 74 int32_t handle, 75 uint32_t code, 76 const Parcel& data, 77 status_t* statusBuffer); 78 status_t executeCommand(int32_t command); 79 void clearCaller(); 80 static void threadDestructor(void *st); 81 static void freeBuffer(Parcel* parcel, 82 const uint8_t* data, size_t dataSize, 83 const size_t* objects, size_t objectsSize, 84 void* cookie); 85 const sp<ProcessState> mProcess; 86 const pid_t mMyThreadId; 87 Vector<BBinder*> mPendingStrongDerefs; 88 Vector<RefBase::weakref_type*> mPendingWeakDerefs; 89 90 Parcel mIn; 91 Parcel mOut; 92 status_t mLastError; 93 pid_t mCallingPid; 94 uid_t mCallingUid; 95 int32_t mStrictModePolicy; 96 int32_t mLastTransactionBinderFlags; 97 }; 98 }; 99 #endif // ANDROID_IPC_THREAD_STATE_H
- IPCThreadState.cpp
-
1 /** 2 * Copyright (C) 2005 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #define LOG_TAG "IPCThreadState" 18 19 #include <binder/IPCThreadState.h> 20 21 #include <binder/Binder.h> 22 #include <binder/BpBinder.h> 23 #include <cutils/sched_policy.h> 24 #include <utils/Debug.h> 25 #include <utils/Log.h> 26 #include <utils/TextOutput.h> 27 #include <utils/threads.h> 28 29 #include <private/binder/binder_module.h> 30 #include <private/binder/Static.h> 31 32 #include <sys/ioctl.h> 33 #include <signal.h> 34 #include <errno.h> 35 #include <stdio.h> 36 #include <unistd.h> 37 38 #ifdef HAVE_PTHREADS 39 #include <pthread.h> 40 #include <sched.h> 41 #include <sys/resource.h> 42 #endif 43 #ifdef HAVE_WIN32_THREADS 44 #include <windows.h> 45 #endif 46 47 48 #if LOG_NDEBUG 49 50 #define IF_LOG_TRANSACTIONS() if (false) 51 #define IF_LOG_COMMANDS() if (false) 52 #define LOG_REMOTEREFS(...) 53 #define IF_LOG_REMOTEREFS() if (false) 54 #define LOG_THREADPOOL(...) 55 #define LOG_ONEWAY(...) 56 57 #else 58 59 #define IF_LOG_TRANSACTIONS() IF_LOG(LOG_VERBOSE, "transact") 60 #define IF_LOG_COMMANDS() IF_LOG(LOG_VERBOSE, "ipc") 61 #define LOG_REMOTEREFS(...) LOG(LOG_DEBUG, "remoterefs", __VA_ARGS__) 62 #define IF_LOG_REMOTEREFS() IF_LOG(LOG_DEBUG, "remoterefs") 63 #define LOG_THREADPOOL(...) LOG(LOG_DEBUG, "threadpool", __VA_ARGS__) 64 #define LOG_ONEWAY(...) LOG(LOG_DEBUG, "ipc", __VA_ARGS__) 65 66 #endif 67 68 // --------------------------------------------------------------------------- 69 70 namespace android { 71 72 static const char* getReturnString(size_t idx); 73 static const char* getCommandString(size_t idx); 74 static const void* printReturnCommand(TextOutput& out, const void* _cmd); 75 static const void* printCommand(TextOutput& out, const void* _cmd); 76 77 // This will result in a missing symbol failure if the IF_LOG_COMMANDS() 78 // conditionals don't get stripped... but that is probably what we want. 79 #if !LOG_NDEBUG 80 static const char *kReturnStrings[] = { 81 "BR_ERROR", 82 "BR_OK", 83 "BR_TRANSACTION", 84 "BR_REPLY", 85 "BR_ACQUIRE_RESULT", 86 "BR_DEAD_REPLY", 87 "BR_TRANSACTION_COMPLETE", 88 "BR_INCREFS", 89 "BR_ACQUIRE", 90 "BR_RELEASE", 91 "BR_DECREFS", 92 "BR_ATTEMPT_ACQUIRE", 93 "BR_NOOP", 94 "BR_SPAWN_LOOPER", 95 "BR_FINISHED", 96 "BR_DEAD_BINDER", 97 "BR_CLEAR_DEATH_NOTIFICATION_DONE", 98 "BR_FAILED_REPLY" 99 }; 100 101 static const char *kCommandStrings[] = { 102 "BC_TRANSACTION", 103 "BC_REPLY", 104 "BC_ACQUIRE_RESULT", 105 "BC_FREE_BUFFER", 106 "BC_INCREFS", 107 "BC_ACQUIRE", 108 "BC_RELEASE", 109 "BC_DECREFS", 110 "BC_INCREFS_DONE", 111 "BC_ACQUIRE_DONE", 112 "BC_ATTEMPT_ACQUIRE", 113 "BC_REGISTER_LOOPER", 114 "BC_ENTER_LOOPER", 115 "BC_EXIT_LOOPER", 116 "BC_REQUEST_DEATH_NOTIFICATION", 117 "BC_CLEAR_DEATH_NOTIFICATION", 118 "BC_DEAD_BINDER_DONE" 119 }; 120 121 static const char* getReturnString(size_t idx) 122 { 123 if (idx < sizeof(kReturnStrings) / sizeof(kReturnStrings[0])) 124 return kReturnStrings[idx]; 125 else 126 return "unknown"; 127 } 128 129 static const char* getCommandString(size_t idx) 130 { 131 if (idx < sizeof(kCommandStrings) / sizeof(kCommandStrings[0])) 132 return kCommandStrings[idx]; 133 else 134 return "unknown"; 135 } 136 137 static const void* printBinderTransactionData(TextOutput& out, const void* data) 138 { 139 const binder_transaction_data* btd = 140 (const binder_transaction_data*)data; 141 if (btd->target.handle < 1024) { 142 /** want to print descriptors in decimal; guess based on value */ 143 out << "target.desc=" << btd->target.handle; 144 } else { 145 out << "target.ptr=" << btd->target.ptr; 146 } 147 out << " (cookie " << btd->cookie << ")" << endl 148 << "code=" << TypeCode(btd->code) << ", flags=" << (void*)btd->flags << endl 149 << "data=" << btd->data.ptr.buffer << " (" << (void*)btd->data_size 150 << " bytes)" << endl 151 << "offsets=" << btd->data.ptr.offsets << " (" << (void*)btd->offsets_size 152 << " bytes)"; 153 return btd+1; 154 } 155 156 static const void* printReturnCommand(TextOutput& out, const void* _cmd) 157 { 158 static const size_t N = sizeof(kReturnStrings)/sizeof(kReturnStrings[0]); 159 const int32_t* cmd = (const int32_t*)_cmd; 160 int32_t code = *cmd++; 161 size_t cmdIndex = code & 0xff; 162 if (code == (int32_t) BR_ERROR) { 163 out << "BR_ERROR: " << (void*)(*cmd++) << endl; 164 return cmd; 165 } else if (cmdIndex >= N) { 166 out << "Unknown reply: " << code << endl; 167 return cmd; 168 } 169 out << kReturnStrings[cmdIndex]; 170 171 switch (code) { 172 case BR_TRANSACTION: 173 case BR_REPLY: { 174 out << ": " << indent; 175 cmd = (const int32_t *)printBinderTransactionData(out, cmd); 176 out << dedent; 177 } break; 178 179 case BR_ACQUIRE_RESULT: { 180 const int32_t res = *cmd++; 181 out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)"); 182 } break; 183 184 case BR_INCREFS: 185 case BR_ACQUIRE: 186 case BR_RELEASE: 187 case BR_DECREFS: { 188 const int32_t b = *cmd++; 189 const int32_t c = *cmd++; 190 out << ": target=" << (void*)b << " (cookie " << (void*)c << ")"; 191 } break; 192 193 case BR_ATTEMPT_ACQUIRE: { 194 const int32_t p = *cmd++; 195 const int32_t b = *cmd++; 196 const int32_t c = *cmd++; 197 out << ": target=" << (void*)b << " (cookie " << (void*)c 198 << "), pri=" << p; 199 } break; 200 201 case BR_DEAD_BINDER: 202 case BR_CLEAR_DEATH_NOTIFICATION_DONE: { 203 const int32_t c = *cmd++; 204 out << ": death cookie " << (void*)c; 205 } break; 206 207 default: 208 // no details to show for: BR_OK, BR_DEAD_REPLY, 209 // BR_TRANSACTION_COMPLETE, BR_FINISHED 210 break; 211 } 212 213 out << endl; 214 return cmd; 215 } 216 217 static const void* printCommand(TextOutput& out, const void* _cmd) 218 { 219 static const size_t N = sizeof(kCommandStrings)/sizeof(kCommandStrings[0]); 220 const int32_t* cmd = (const int32_t*)_cmd; 221 int32_t code = *cmd++; 222 size_t cmdIndex = code & 0xff; 223 224 if (cmdIndex >= N) { 225 out << "Unknown command: " << code << endl; 226 return cmd; 227 } 228 out << kCommandStrings[cmdIndex]; 229 230 switch (code) { 231 case BC_TRANSACTION: 232 case BC_REPLY: { 233 out << ": " << indent; 234 cmd = (const int32_t *)printBinderTransactionData(out, cmd); 235 out << dedent; 236 } break; 237 238 case BC_ACQUIRE_RESULT: { 239 const int32_t res = *cmd++; 240 out << ": " << res << (res ? " (SUCCESS)" : " (FAILURE)"); 241 } break; 242 243 case BC_FREE_BUFFER: { 244 const int32_t buf = *cmd++; 245 out << ": buffer=" << (void*)buf; 246 } break; 247 248 case BC_INCREFS: 249 case BC_ACQUIRE: 250 case BC_RELEASE: 251 case BC_DECREFS: { 252 const int32_t d = *cmd++; 253 out << ": desc=" << d; 254 } break; 255 256 case BC_INCREFS_DONE: 257 case BC_ACQUIRE_DONE: { 258 const int32_t b = *cmd++; 259 const int32_t c = *cmd++; 260 out << ": target=" << (void*)b << " (cookie " << (void*)c << ")"; 261 } break; 262 263 case BC_ATTEMPT_ACQUIRE: { 264 const int32_t p = *cmd++; 265 const int32_t d = *cmd++; 266 out << ": desc=" << d << ", pri=" << p; 267 } break; 268 269 case BC_REQUEST_DEATH_NOTIFICATION: 270 case BC_CLEAR_DEATH_NOTIFICATION: { 271 const int32_t h = *cmd++; 272 const int32_t c = *cmd++; 273 out << ": handle=" << h << " (death cookie " << (void*)c << ")"; 274 } break; 275 276 case BC_DEAD_BINDER_DONE: { 277 const int32_t c = *cmd++; 278 out << ": death cookie " << (void*)c; 279 } break; 280 281 default: 282 // no details to show for: BC_REGISTER_LOOPER, BC_ENTER_LOOPER, 283 // BC_EXIT_LOOPER 284 break; 285 } 286 287 out << endl; 288 return cmd; 289 } 290 #endif 291 292 static pthread_mutex_t gTLSMutex = PTHREAD_MUTEX_INITIALIZER; 293 static bool gHaveTLS = false; 294 static pthread_key_t gTLS = 0; 295 static bool gShutdown = false; 296 static bool gDisableBackgroundScheduling = false; 297 298 IPCThreadState* IPCThreadState::self() 299 { 300 if (gHaveTLS) { 301 restart: 302 const pthread_key_t k = gTLS; 303 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k); 304 if (st) return st; 305 return new IPCThreadState; 306 } 307 if (gShutdown) return NULL; 308 pthread_mutex_lock(&gTLSMutex); 309 if (!gHaveTLS) { 310 if (pthread_key_create(&gTLS, threadDestructor) != 0) { 311 pthread_mutex_unlock(&gTLSMutex); 312 return NULL; 313 } 314 gHaveTLS = true; 315 } 316 pthread_mutex_unlock(&gTLSMutex); 317 goto restart; 318 } 319 320 IPCThreadState* IPCThreadState::selfOrNull() 321 { 322 if (gHaveTLS) { 323 const pthread_key_t k = gTLS; 324 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k); 325 return st; 326 } 327 return NULL; 328 } 329 330 void IPCThreadState::shutdown() 331 { 332 gShutdown = true; 333 334 if (gHaveTLS) { 335 // XXX Need to wait for all thread pool threads to exit! 336 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(gTLS); 337 if (st) { 338 delete st; 339 pthread_setspecific(gTLS, NULL); 340 } 341 gHaveTLS = false; 342 } 343 } 344 345 void IPCThreadState::disableBackgroundScheduling(bool disable) 346 { 347 gDisableBackgroundScheduling = disable; 348 } 349 350 sp<ProcessState> IPCThreadState::process() 351 { 352 return mProcess; 353 } 354 355 status_t IPCThreadState::clearLastError() 356 { 357 const status_t err = mLastError; 358 mLastError = NO_ERROR; 359 return err; 360 } 361 362 int IPCThreadState::getCallingPid() 363 { 364 return mCallingPid; 365 } 366 367 int IPCThreadState::getCallingUid() 368 { 369 return mCallingUid; 370 } 371 372 int64_t IPCThreadState::clearCallingIdentity() 373 { 374 int64_t token = ((int64_t)mCallingUid<<32) | mCallingPid; 375 clearCaller(); 376 return token; 377 } 378 379 void IPCThreadState::setStrictModePolicy(int32_t policy) 380 { 381 mStrictModePolicy = policy; 382 } 383 384 int32_t IPCThreadState::getStrictModePolicy() const 385 { 386 return mStrictModePolicy; 387 } 388 389 void IPCThreadState::setLastTransactionBinderFlags(int32_t flags) 390 { 391 mLastTransactionBinderFlags = flags; 392 } 393 394 int32_t IPCThreadState::getLastTransactionBinderFlags() const 395 { 396 return mLastTransactionBinderFlags; 397 } 398 399 void IPCThreadState::restoreCallingIdentity(int64_t token) 400 { 401 mCallingUid = (int)(token>>32); 402 mCallingPid = (int)token; 403 } 404 405 void IPCThreadState::clearCaller() 406 { 407 mCallingPid = getpid(); 408 mCallingUid = getuid(); 409 } 410 411 void IPCThreadState::flushCommands() 412 { 413 if (mProcess->mDriverFD <= 0) 414 return; 415 talkWithDriver(false); 416 } 417 418 void IPCThreadState::joinThreadPool(bool isMain) 419 { 420 LOG_THREADPOOL("**** THREAD %p (PID %d) IS JOINING THE THREAD POOL\n", (void*)pthread_self(), getpid()); 421 mOut.writeInt32(isMain ? BC_ENTER_LOOPER : BC_REGISTER_LOOPER); 422 // This thread may have been spawned by a thread that was in the background 423 // scheduling group, so first we will make sure it is in the default/foreground 424 // one to avoid performing an initial transaction in the background. 425 androidSetThreadSchedulingGroup(mMyThreadId, ANDROID_TGROUP_DEFAULT); 426 status_t result; 427 do { 428 int32_t cmd; 429 // When we've cleared the incoming command queue, process any pending derefs 430 if (mIn.dataPosition() >= mIn.dataSize()) { 431 size_t numPending = mPendingWeakDerefs.size(); 432 if (numPending > 0) { 433 for (size_t i = 0; i < numPending; i++) { 434 RefBase::weakref_type* refs = mPendingWeakDerefs[i]; 435 refs->decWeak(mProcess.get()); 436 } 437 mPendingWeakDerefs.clear(); 438 } 439 numPending = mPendingStrongDerefs.size(); 440 if (numPending > 0) { 441 for (size_t i = 0; i < numPending; i++) { 442 BBinder* obj = mPendingStrongDerefs[i]; 443 obj->decStrong(mProcess.get()); 444 } 445 mPendingStrongDerefs.clear(); 446 } 447 } 448 // now get the next command to be processed, waiting if necessary 449 result = talkWithDriver(); 450 if (result >= NO_ERROR) { 451 size_t IN = mIn.dataAvail(); 452 if (IN < sizeof(int32_t)) continue; 453 cmd = mIn.readInt32(); 454 IF_LOG_COMMANDS() { 455 alog << "Processing top-level Command: " 456 << getReturnString(cmd) << endl; 457 } 458 result = executeCommand(cmd); 459 } 460 // After executing the command, ensure that the thread is returned to the 461 // default cgroup before rejoining the pool. The driver takes care of 462 // restoring the priority, but doesn't do anything with cgroups so we 463 // need to take care of that here in userspace. Note that we do make 464 // sure to go in the foreground after executing a transaction, but 465 // there are other callbacks into user code that could have changed 466 // our group so we want to make absolutely sure it is put back. 467 androidSetThreadSchedulingGroup(mMyThreadId, ANDROID_TGROUP_DEFAULT); 468 // Let this thread exit the thread pool if it is no longer 469 // needed and it is not the main process thread. 470 if(result == TIMED_OUT && !isMain) { 471 break; 472 } 473 } while (result != -ECONNREFUSED && result != -EBADF); 474 475 LOG_THREADPOOL("**** THREAD %p (PID %d) IS LEAVING THE THREAD POOL err=%p\n", 476 (void*)pthread_self(), getpid(), (void*)result); 477 mOut.writeInt32(BC_EXIT_LOOPER); 478 talkWithDriver(false); 479 } 480 481 void IPCThreadState::stopProcess(bool immediate) 482 { 483 //LOGI("**** STOPPING PROCESS"); 484 flushCommands(); 485 int fd = mProcess->mDriverFD; 486 mProcess->mDriverFD = -1; 487 close(fd); 488 //kill(getpid(), SIGKILL); 489 } 490 491 status_t IPCThreadState::transact(int32_t handle, 492 uint32_t code, const Parcel& data, 493 Parcel* reply, uint32_t flags) 494 { 495 status_t err = data.errorCheck(); 496 497 flags |= TF_ACCEPT_FDS; 498 499 IF_LOG_TRANSACTIONS() { 500 TextOutput::Bundle _b(alog); 501 alog << "BC_TRANSACTION thr " << (void*)pthread_self() << " / hand " 502 << handle << " / code " << TypeCode(code) << ": " 503 << indent << data << dedent << endl; 504 } 505 506 if (err == NO_ERROR) { 507 LOG_ONEWAY(">>>> SEND from pid %d uid %d %s", getpid(), getuid(), 508 (flags & TF_ONE_WAY) == 0 ? "READ REPLY" : "ONE WAY"); 509 err = writeTransactionData(BC_TRANSACTION, flags, handle, code, data, NULL); 510 } 511 512 if (err != NO_ERROR) { 513 if (reply) reply->setError(err); 514 return (mLastError = err); 515 } 516 517 if ((flags & TF_ONE_WAY) == 0) { 518 #if 0 519 if (code == 4) { // relayout 520 LOGI(">>>>>> CALLING transaction 4"); 521 } else { 522 LOGI(">>>>>> CALLING transaction %d", code); 523 } 524 #endif 525 if (reply) { 526 err = waitForResponse(reply); 527 } else { 528 Parcel fakeReply; 529 err = waitForResponse(&fakeReply); 530 } 531 #if 0 532 if (code == 4) { // relayout 533 LOGI("<<<<<< RETURNING transaction 4"); 534 } else { 535 LOGI("<<<<<< RETURNING transaction %d", code); 536 } 537 #endif 538 539 IF_LOG_TRANSACTIONS() { 540 TextOutput::Bundle _b(alog); 541 alog << "BR_REPLY thr " << (void*)pthread_self() << " / hand " 542 << handle << ": "; 543 if (reply) alog << indent << *reply << dedent << endl; 544 else alog << "(none requested)" << endl; 545 } 546 } else { 547 err = waitForResponse(NULL, NULL); 548 } 549 550 return err; 551 } 552 553 void IPCThreadState::incStrongHandle(int32_t handle) 554 { 555 LOG_REMOTEREFS("IPCThreadState::incStrongHandle(%d)\n", handle); 556 mOut.writeInt32(BC_ACQUIRE); 557 mOut.writeInt32(handle); 558 } 559 560 void IPCThreadState::decStrongHandle(int32_t handle) 561 { 562 LOG_REMOTEREFS("IPCThreadState::decStrongHandle(%d)\n", handle); 563 mOut.writeInt32(BC_RELEASE); 564 mOut.writeInt32(handle); 565 } 566 567 void IPCThreadState::incWeakHandle(int32_t handle) 568 { 569 LOG_REMOTEREFS("IPCThreadState::incWeakHandle(%d)\n", handle); 570 mOut.writeInt32(BC_INCREFS); 571 mOut.writeInt32(handle); 572 } 573 574 void IPCThreadState::decWeakHandle(int32_t handle) 575 { 576 LOG_REMOTEREFS("IPCThreadState::decWeakHandle(%d)\n", handle); 577 mOut.writeInt32(BC_DECREFS); 578 mOut.writeInt32(handle); 579 } 580 581 status_t IPCThreadState::attemptIncStrongHandle(int32_t handle) 582 { 583 LOG_REMOTEREFS("IPCThreadState::attemptIncStrongHandle(%d)\n", handle); 584 mOut.writeInt32(BC_ATTEMPT_ACQUIRE); 585 mOut.writeInt32(0); // xxx was thread priority 586 mOut.writeInt32(handle); 587 status_t result = UNKNOWN_ERROR; 588 589 waitForResponse(NULL, &result); 590 591 #if LOG_REFCOUNTS 592 printf("IPCThreadState::attemptIncStrongHandle(%ld) = %s\n", 593 handle, result == NO_ERROR ? "SUCCESS" : "FAILURE"); 594 #endif 595 596 return result; 597 } 598 599 void IPCThreadState::expungeHandle(int32_t handle, IBinder* binder) 600 { 601 #if LOG_REFCOUNTS 602 printf("IPCThreadState::expungeHandle(%ld)\n", handle); 603 #endif 604 self()->mProcess->expungeHandle(handle, binder); 605 } 606 607 status_t IPCThreadState::requestDeathNotification(int32_t handle, BpBinder* proxy) 608 { 609 mOut.writeInt32(BC_REQUEST_DEATH_NOTIFICATION); 610 mOut.writeInt32((int32_t)handle); 611 mOut.writeInt32((int32_t)proxy); 612 return NO_ERROR; 613 } 614 615 status_t IPCThreadState::clearDeathNotification(int32_t handle, BpBinder* proxy) 616 { 617 mOut.writeInt32(BC_CLEAR_DEATH_NOTIFICATION); 618 mOut.writeInt32((int32_t)handle); 619 mOut.writeInt32((int32_t)proxy); 620 return NO_ERROR; 621 } 622 623 IPCThreadState::IPCThreadState() 624 : mProcess(ProcessState::self()), 625 mMyThreadId(androidGetTid()), 626 mStrictModePolicy(0), 627 mLastTransactionBinderFlags(0) 628 { 629 pthread_setspecific(gTLS, this); 630 clearCaller(); 631 mIn.setDataCapacity(256); 632 mOut.setDataCapacity(256); 633 } 634 635 IPCThreadState::~IPCThreadState() 636 { 637 } 638 639 status_t IPCThreadState::sendReply(const Parcel& reply, uint32_t flags) 640 { 641 status_t err; 642 status_t statusBuffer; 643 err = writeTransactionData(BC_REPLY, flags, -1, 0, reply, &statusBuffer); 644 if (err < NO_ERROR) return err; 645 646 return waitForResponse(NULL, NULL); 647 } 648 649 status_t IPCThreadState::waitForResponse(Parcel *reply, status_t *acquireResult) 650 { 651 int32_t cmd; 652 int32_t err; 653 654 while (1) { 655 if ((err=talkWithDriver()) < NO_ERROR) break; 656 err = mIn.errorCheck(); 657 if (err < NO_ERROR) break; 658 if (mIn.dataAvail() == 0) continue; 659 660 cmd = mIn.readInt32(); 661 662 IF_LOG_COMMANDS() { 663 alog << "Processing waitForResponse Command: " 664 << getReturnString(cmd) << endl; 665 } 666 667 switch (cmd) { 668 case BR_TRANSACTION_COMPLETE: 669 if (!reply && !acquireResult) goto finish; 670 break; 671 672 case BR_DEAD_REPLY: 673 err = DEAD_OBJECT; 674 goto finish; 675 676 case BR_FAILED_REPLY: 677 err = FAILED_TRANSACTION; 678 goto finish; 679 680 case BR_ACQUIRE_RESULT: 681 { 682 LOG_ASSERT(acquireResult != NULL, "Unexpected brACQUIRE_RESULT"); 683 const int32_t result = mIn.readInt32(); 684 if (!acquireResult) continue; 685 *acquireResult = result ? NO_ERROR : INVALID_OPERATION; 686 } 687 goto finish; 688 689 case BR_REPLY: 690 { 691 binder_transaction_data tr; 692 err = mIn.read(&tr, sizeof(tr)); 693 LOG_ASSERT(err == NO_ERROR, "Not enough command data for brREPLY"); 694 if (err != NO_ERROR) goto finish; 695 696 if (reply) { 697 if ((tr.flags & TF_STATUS_CODE) == 0) { 698 reply->ipcSetDataReference( 699 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), 700 tr.data_size, 701 reinterpret_cast<const size_t*>(tr.data.ptr.offsets), 702 tr.offsets_size/sizeof(size_t), 703 freeBuffer, this); 704 } else { 705 err = *static_cast<const status_t*>(tr.data.ptr.buffer); 706 freeBuffer(NULL, 707 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), 708 tr.data_size, 709 reinterpret_cast<const size_t*>(tr.data.ptr.offsets), 710 tr.offsets_size/sizeof(size_t), this); 711 } 712 } else { 713 freeBuffer(NULL, 714 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), 715 tr.data_size, 716 reinterpret_cast<const size_t*>(tr.data.ptr.offsets), 717 tr.offsets_size/sizeof(size_t), this); 718 continue; 719 } 720 } 721 goto finish; 722 723 default: 724 err = executeCommand(cmd); 725 if (err != NO_ERROR) goto finish; 726 break; 727 } 728 } 729 730 finish: 731 if (err != NO_ERROR) { 732 if (acquireResult) *acquireResult = err; 733 if (reply) reply->setError(err); 734 mLastError = err; 735 } 736 737 return err; 738 } 739 740 status_t IPCThreadState::talkWithDriver(bool doReceive) 741 { 742 LOG_ASSERT(mProcess->mDriverFD >= 0, "Binder driver is not opened"); 743 744 binder_write_read bwr; 745 746 // Is the read buffer empty? 747 const bool needRead = mIn.dataPosition() >= mIn.dataSize(); 748 749 // We don't want to write anything if we are still reading 750 // from data left in the input buffer and the caller 751 // has requested to read the next data. 752 const size_t outAvail = (!doReceive || needRead) ? mOut.dataSize() : 0; 753 754 bwr.write_size = outAvail; 755 bwr.write_buffer = (long unsigned int)mOut.data(); 756 757 // This is what we'll read. 758 if (doReceive && needRead) { 759 bwr.read_size = mIn.dataCapacity(); 760 bwr.read_buffer = (long unsigned int)mIn.data(); 761 } else { 762 bwr.read_size = 0; 763 } 764 765 IF_LOG_COMMANDS() { 766 TextOutput::Bundle _b(alog); 767 if (outAvail != 0) { 768 alog << "Sending commands to driver: " << indent; 769 const void* cmds = (const void*)bwr.write_buffer; 770 const void* end = ((const uint8_t*)cmds)+bwr.write_size; 771 alog << HexDump(cmds, bwr.write_size) << endl; 772 while (cmds < end) cmds = printCommand(alog, cmds); 773 alog << dedent; 774 } 775 alog << "Size of receive buffer: " << bwr.read_size 776 << ", needRead: " << needRead << ", doReceive: " << doReceive << endl; 777 } 778 779 // Return immediately if there is nothing to do. 780 if ((bwr.write_size == 0) && (bwr.read_size == 0)) return NO_ERROR; 781 782 bwr.write_consumed = 0; 783 bwr.read_consumed = 0; 784 status_t err; 785 do { 786 IF_LOG_COMMANDS() { 787 alog << "About to read/write, write size = " << mOut.dataSize() << endl; 788 } 789 #if defined(HAVE_ANDROID_OS) 790 if (ioctl(mProcess->mDriverFD, BINDER_WRITE_READ, &bwr) >= 0) 791 err = NO_ERROR; 792 else 793 err = -errno; 794 #else 795 err = INVALID_OPERATION; 796 #endif 797 IF_LOG_COMMANDS() { 798 alog << "Finished read/write, write size = " << mOut.dataSize() << endl; 799 } 800 } while (err == -EINTR); 801 802 IF_LOG_COMMANDS() { 803 alog << "Our err: " << (void*)err << ", write consumed: " 804 << bwr.write_consumed << " (of " << mOut.dataSize() 805 << "), read consumed: " << bwr.read_consumed << endl; 806 } 807 808 if (err >= NO_ERROR) { 809 if (bwr.write_consumed > 0) { 810 if (bwr.write_consumed < (ssize_t)mOut.dataSize()) 811 mOut.remove(0, bwr.write_consumed); 812 else 813 mOut.setDataSize(0); 814 } 815 if (bwr.read_consumed > 0) { 816 mIn.setDataSize(bwr.read_consumed); 817 mIn.setDataPosition(0); 818 } 819 IF_LOG_COMMANDS() { 820 TextOutput::Bundle _b(alog); 821 alog << "Remaining data size: " << mOut.dataSize() << endl; 822 alog << "Received commands from driver: " << indent; 823 const void* cmds = mIn.data(); 824 const void* end = mIn.data() + mIn.dataSize(); 825 alog << HexDump(cmds, mIn.dataSize()) << endl; 826 while (cmds < end) cmds = printReturnCommand(alog, cmds); 827 alog << dedent; 828 } 829 return NO_ERROR; 830 } 831 832 return err; 833 } 834 835 status_t IPCThreadState::writeTransactionData(int32_t cmd, uint32_t binderFlags, 836 int32_t handle, uint32_t code, const Parcel& data, status_t* statusBuffer) 837 { 838 binder_transaction_data tr; 839 840 tr.target.handle = handle; 841 tr.code = code; 842 tr.flags = binderFlags; 843 tr.cookie = 0; 844 tr.sender_pid = 0; 845 tr.sender_euid = 0; 846 847 const status_t err = data.errorCheck(); 848 if (err == NO_ERROR) { 849 tr.data_size = data.ipcDataSize(); 850 tr.data.ptr.buffer = data.ipcData(); 851 tr.offsets_size = data.ipcObjectsCount()*sizeof(size_t); 852 tr.data.ptr.offsets = data.ipcObjects(); 853 } else if (statusBuffer) { 854 tr.flags |= TF_STATUS_CODE; 855 *statusBuffer = err; 856 tr.data_size = sizeof(status_t); 857 tr.data.ptr.buffer = statusBuffer; 858 tr.offsets_size = 0; 859 tr.data.ptr.offsets = NULL; 860 } else { 861 return (mLastError = err); 862 } 863 864 mOut.writeInt32(cmd); 865 mOut.write(&tr, sizeof(tr)); 866 867 return NO_ERROR; 868 } 869 870 sp<BBinder> the_context_object; 871 872 void setTheContextObject(sp<BBinder> obj) 873 { 874 the_context_object = obj; 875 } 876 877 status_t IPCThreadState::executeCommand(int32_t cmd) 878 { 879 BBinder* obj; 880 RefBase::weakref_type* refs; 881 status_t result = NO_ERROR; 882 883 switch (cmd) { 884 case BR_ERROR: 885 result = mIn.readInt32(); 886 break; 887 888 case BR_OK: 889 break; 890 891 case BR_ACQUIRE: 892 refs = (RefBase::weakref_type*)mIn.readInt32(); 893 obj = (BBinder*)mIn.readInt32(); 894 LOG_ASSERT(refs->refBase() == obj, 895 "BR_ACQUIRE: object %p does not match cookie %p (expected %p)", 896 refs, obj, refs->refBase()); 897 obj->incStrong(mProcess.get()); 898 IF_LOG_REMOTEREFS() { 899 LOG_REMOTEREFS("BR_ACQUIRE from driver on %p", obj); 900 obj->printRefs(); 901 } 902 mOut.writeInt32(BC_ACQUIRE_DONE); 903 mOut.writeInt32((int32_t)refs); 904 mOut.writeInt32((int32_t)obj); 905 break; 906 907 case BR_RELEASE: 908 refs = (RefBase::weakref_type*)mIn.readInt32(); 909 obj = (BBinder*)mIn.readInt32(); 910 LOG_ASSERT(refs->refBase() == obj, 911 "BR_RELEASE: object %p does not match cookie %p (expected %p)", 912 refs, obj, refs->refBase()); 913 IF_LOG_REMOTEREFS() { 914 LOG_REMOTEREFS("BR_RELEASE from driver on %p", obj); 915 obj->printRefs(); 916 } 917 mPendingStrongDerefs.push(obj); 918 break; 919 920 case BR_INCREFS: 921 refs = (RefBase::weakref_type*)mIn.readInt32(); 922 obj = (BBinder*)mIn.readInt32(); 923 refs->incWeak(mProcess.get()); 924 mOut.writeInt32(BC_INCREFS_DONE); 925 mOut.writeInt32((int32_t)refs); 926 mOut.writeInt32((int32_t)obj); 927 break; 928 929 case BR_DECREFS: 930 refs = (RefBase::weakref_type*)mIn.readInt32(); 931 obj = (BBinder*)mIn.readInt32(); 932 // NOTE: This assertion is not valid, because the object may no 933 // longer exist (thus the (BBinder*)cast above resulting in a different 934 // memory address). 935 //LOG_ASSERT(refs->refBase() == obj, 936 // "BR_DECREFS: object %p does not match cookie %p (expected %p)", 937 // refs, obj, refs->refBase()); 938 mPendingWeakDerefs.push(refs); 939 break; 940 941 case BR_ATTEMPT_ACQUIRE: 942 refs = (RefBase::weakref_type*)mIn.readInt32(); 943 obj = (BBinder*)mIn.readInt32(); 944 945 { 946 const bool success = refs->attemptIncStrong(mProcess.get()); 947 LOG_ASSERT(success && refs->refBase() == obj, 948 "BR_ATTEMPT_ACQUIRE: object %p does not match cookie %p (expected %p)", 949 refs, obj, refs->refBase()); 950 951 mOut.writeInt32(BC_ACQUIRE_RESULT); 952 mOut.writeInt32((int32_t)success); 953 } 954 break; 955 956 case BR_TRANSACTION: 957 { 958 binder_transaction_data tr; 959 result = mIn.read(&tr, sizeof(tr)); 960 LOG_ASSERT(result == NO_ERROR, 961 "Not enough command data for brTRANSACTION"); 962 if (result != NO_ERROR) break; 963 964 Parcel buffer; 965 buffer.ipcSetDataReference( 966 reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer), 967 tr.data_size, 968 reinterpret_cast<const size_t*>(tr.data.ptr.offsets), 969 tr.offsets_size/sizeof(size_t), freeBuffer, this); 970 971 const pid_t origPid = mCallingPid; 972 const uid_t origUid = mCallingUid; 973 974 mCallingPid = tr.sender_pid; 975 mCallingUid = tr.sender_euid; 976 977 int curPrio = getpriority(PRIO_PROCESS, mMyThreadId); 978 if (gDisableBackgroundScheduling) { 979 if (curPrio > ANDROID_PRIORITY_NORMAL) { 980 // We have inherited a reduced priority from the caller, but do not 981 // want to run in that state in this process. The driver set our 982 // priority already (though not our scheduling class), so bounce 983 // it back to the default before invoking the transaction. 984 setpriority(PRIO_PROCESS, mMyThreadId, ANDROID_PRIORITY_NORMAL); 985 } 986 } else { 987 if (curPrio >= ANDROID_PRIORITY_BACKGROUND) { 988 // We want to use the inherited priority from the caller. 989 // Ensure this thread is in the background scheduling class, 990 // since the driver won't modify scheduling classes for us. 991 // The scheduling group is reset to default by the caller 992 // once this method returns after the transaction is complete. 993 androidSetThreadSchedulingGroup(mMyThreadId, 994 ANDROID_TGROUP_BG_NONINTERACT); 995 } 996 } 997 998 //LOGI(">>>> TRANSACT from pid %d uid %d\n", mCallingPid, mCallingUid); 999 1000 Parcel reply; 1001 IF_LOG_TRANSACTIONS() { 1002 TextOutput::Bundle _b(alog); 1003 alog << "BR_TRANSACTION thr " << (void*)pthread_self() 1004 << " / obj " << tr.target.ptr << " / code " 1005 << TypeCode(tr.code) << ": " << indent << buffer 1006 << dedent << endl 1007 << "Data addr = " 1008 << reinterpret_cast<const uint8_t*>(tr.data.ptr.buffer) 1009 << ", offsets addr=" 1010 << reinterpret_cast<const size_t*>(tr.data.ptr.offsets) << endl; 1011 } 1012 if (tr.target.ptr) { 1013 sp<BBinder> b((BBinder*)tr.cookie); 1014 const status_t error = b->transact(tr.code, buffer, &reply, tr.flags); 1015 if (error < NO_ERROR) reply.setError(error); 1016 1017 } else { 1018 const status_t error = the_context_object->transact(tr.code, buffer, &reply, tr.flags); 1019 if (error < NO_ERROR) reply.setError(error); 1020 } 1021 1022 //LOGI("<<<< TRANSACT from pid %d restore pid %d uid %d\n", 1023 // mCallingPid, origPid, origUid); 1024 1025 if ((tr.flags & TF_ONE_WAY) == 0) { 1026 LOG_ONEWAY("Sending reply to %d!", mCallingPid); 1027 sendReply(reply, 0); 1028 } else { 1029 LOG_ONEWAY("NOT sending reply to %d!", mCallingPid); 1030 } 1031 1032 mCallingPid = origPid; 1033 mCallingUid = origUid; 1034 1035 IF_LOG_TRANSACTIONS() { 1036 TextOutput::Bundle _b(alog); 1037 alog << "BC_REPLY thr " << (void*)pthread_self() << " / obj " 1038 << tr.target.ptr << ": " << indent << reply << dedent << endl; 1039 } 1040 1041 } 1042 break; 1043 1044 case BR_DEAD_BINDER: 1045 { 1046 BpBinder *proxy = (BpBinder*)mIn.readInt32(); 1047 proxy->sendObituary(); 1048 mOut.writeInt32(BC_DEAD_BINDER_DONE); 1049 mOut.writeInt32((int32_t)proxy); 1050 } break; 1051 1052 case BR_CLEAR_DEATH_NOTIFICATION_DONE: 1053 { 1054 BpBinder *proxy = (BpBinder*)mIn.readInt32(); 1055 proxy->getWeakRefs()->decWeak(proxy); 1056 } break; 1057 1058 case BR_FINISHED: 1059 result = TIMED_OUT; 1060 break; 1061 1062 case BR_NOOP: 1063 break; 1064 1065 case BR_SPAWN_LOOPER: 1066 mProcess->spawnPooledThread(false); 1067 break; 1068 1069 default: 1070 printf("*** BAD COMMAND %d received from Binder driver\n", cmd); 1071 result = UNKNOWN_ERROR; 1072 break; 1073 } 1074 1075 if (result != NO_ERROR) { 1076 mLastError = result; 1077 } 1078 1079 return result; 1080 } 1081 1082 void IPCThreadState::threadDestructor(void *st) 1083 { 1084 IPCThreadState* const self = static_cast<IPCThreadState*>(st); 1085 if (self) { 1086 self->flushCommands(); 1087 #if defined(HAVE_ANDROID_OS) 1088 ioctl(self->mProcess->mDriverFD, BINDER_THREAD_EXIT, 0); 1089 #endif 1090 delete self; 1091 } 1092 } 1093 1094 1095 void IPCThreadState::freeBuffer(Parcel* parcel, const uint8_t* data, size_t dataSize, 1096 const size_t* objects, size_t objectsSize, 1097 void* cookie) 1098 { 1099 //LOGI("Freeing parcel %p", &parcel); 1100 IF_LOG_COMMANDS() { 1101 alog << "Writing BC_FREE_BUFFER for " << data << endl; 1102 } 1103 LOG_ASSERT(data != NULL, "Called with NULL data"); 1104 if (parcel != NULL) parcel->closeFileDescriptors(); 1105 IPCThreadState* state = self(); 1106 state->mOut.writeInt32(BC_FREE_BUFFER); 1107 state->mOut.writeInt32((int32_t)data); 1108 } 1109 1110 }; // namespace android
-
IPCThread.Self()
-
1 static pthread_mutex_t gTLSMutex = PTHREAD_MUTEX_INITIALIZER; 2 static bool gHaveTLS = false; 3 static pthread_key_t gTLS = 0; 4 static bool gShutdown = false; 5 static bool gDisableBackgroundScheduling = false; 6 IPCThreadState* IPCThreadState::self() 7 { 8 if (gHaveTLS) { 9 restart: 10 const pthread_key_t k = gTLS; 11 IPCThreadState* st = (IPCThreadState*)pthread_getspecific(k); 12 if (st) return st; 13 return new IPCThreadState; 14 } 15 if (gShutdown) return NULL; 16 pthread_mutex_lock(&gTLSMutex); 17 if (!gHaveTLS) { 18 if (pthread_key_create(&gTLS, threadDestructor) != 0) { 19 pthread_mutex_unlock(&gTLSMutex); 20 return NULL; 21 } 22 gHaveTLS = true; 23 } 24 pthread_mutex_unlock(&gTLSMutex); 25 goto restart; 26 } 27 IPCThreadState::IPCThreadState() 28 : mProcess(ProcessState::self()), 29 mMyThreadId(androidGetTid()), 30 mStrictModePolicy(0), 31 mLastTransactionBinderFlags(0) 32 { 33 pthread_setspecific(gTLS, this); 34 clearCaller(); 35 mIn.setDataCapacity(256); 36 mOut.setDataCapacity(256); 37 }
- joinThreadPool
-
1 void IPCThreadState::joinThreadPool(bool isMain) 2 { 3 LOG_THREADPOOL("**** THREAD %p (PID %d) IS JOINING THE THREAD POOL\n", (void*)pthread_self(), getpid()); 4 mOut.writeInt32(isMain ? BC_ENTER_LOOPER : BC_REGISTER_LOOPER); 5 androidSetThreadSchedulingGroup(mMyThreadId, ANDROID_TGROUP_DEFAULT); 6 status_t result; 7 do { 8 int32_t cmd; 9 if (mIn.dataPosition() >= mIn.dataSize()) { 10 size_t numPending = mPendingWeakDerefs.size(); 11 if (numPending > 0) { 12 for (size_t i = 0; i < numPending; i++) { 13 RefBase::weakref_type* refs = mPendingWeakDerefs[i]; 14 refs->decWeak(mProcess.get()); 15 } 16 mPendingWeakDerefs.clear(); 17 } 18 numPending = mPendingStrongDerefs.size(); 19 if (numPending > 0) { 20 for (size_t i = 0; i < numPending; i++) { 21 BBinder* obj = mPendingStrongDerefs[i]; 22 obj->decStrong(mProcess.get()); 23 } 24 mPendingStrongDerefs.clear(); 25 } 26 } 27 // now get the next command to be processed, waiting if necessary 28 result = talkWithDriver(); 29 if (result >= NO_ERROR) { 30 size_t IN = mIn.dataAvail(); 31 if (IN < sizeof(int32_t)) continue; 32 cmd = mIn.readInt32(); 33 IF_LOG_COMMANDS() { 34 alog << "Processing top-level Command: " 35 << getReturnString(cmd) << endl; 36 } 37 result = executeCommand(cmd); 38 } 39 androidSetThreadSchedulingGroup(mMyThreadId, ANDROID_TGROUP_DEFAULT); 40 if(result == TIMED_OUT && !isMain) { 41 break; 42 } 43 } while (result != -ECONNREFUSED && result != -EBADF); 44 LOG_THREADPOOL("**** THREAD %p (PID %d) IS LEAVING THE THREAD POOL err=%p\n", 45 (void*)pthread_self(), getpid(), (void*)result); 46 mOut.writeInt32(BC_EXIT_LOOPER); 47 talkWithDriver(false); 48 }