Android Framework层线程设计

framework层的thread是c++实现的,定义在utils/threads.h,实现在Threads.cpp (system\core\libutils)。</pre><pre name="code" class="cpp">首先看看定义:

</pre><pre name="code" class="cpp">class Thread : virtual public RefBase{public:// Create aThread object, but doesn't create or start the associated// thread.See the run() method.Thread(bool canCallJava= true); virtual~Thread();// Startthe thread in threadLoop() which needs to be implemented.virtualstatus_t run( const char* name = 0,int32_tpriority = PRIORITY_DEFAULT,size_t stack =0);// Ask thisobject's thread to exit. This function is asynchronous, when the// functionreturns the thread might still be running. Of course, this// functioncan be called from a different thread.virtualvoidrequestExit();// Goodplace to do one-time initializationsvirtualstatus_t readyToRun();// CallrequestExit() and wait until this object's thread exits.// BE VERYCAREFUL of deadlocks. In particular, it would be silly to call// thisfunction from this object's thread. Will return WOULD_BLOCK in// thatcase.status_t requestExitAndWait();// Waituntil this object's thread exits. Returns immediately if not yet running.// Do notcall from this object's thread; will return WOULD_BLOCK in that case.status_t join();//Indicates whether this thread is running or not.boolisRunning() const; #ifdef HAVE_ANDROID_OS// Returnthe thread's kernel ID, same as the thread itself calling gettid() or//androidGetTid(), or -1 if the thread is not running.pid_tgetTid() const;#endif protected://exitPending() returns true if requestExit() has been called.boolexitPending() const;private:// Derivedclass must implement threadLoop(). The thread starts its life// here.There are two ways of using the Thread object:// 1) loop:if threadLoop() returns true, it will be called again if//requestExit() wasn't called.// 2) once:if threadLoop() returns false, the thread will exit upon return.virtualboolthreadLoop() = 0; private:Thread&operator=(const Thread&);static int_threadLoop(void* user);const boolmCanCallJava;// alwayshold mLock when reading or writingthread_id_tmThread;mutableMutexmLock;ConditionmThreadExitedCondition;status_tmStatus;// notethat all accesses of mExitPending and mRunning need to hold mLockvolatileboolmExitPending;volatileboolmRunning;sp<Thread>mHoldSelf;#ifdef HAVE_ANDROID_OS// legacyfor debugging, not used by getTid() as it is set by the child thread// and sois not initialized until the child reaches that pointpid_tmTid;#endif};

thread继承类RefBase,所以在onFirstRef中,调用了run函数

void AudioFlinger::PlaybackThread::onFirstRef(){run(mName,ANDROID_PRIORITY_URGENT_AUDIO);}status_t Thread::run(const char* name, int32_tpriority, size_t stack){ …if(mCanCallJava) {res =createThreadEtc(_threadLoop,this, name, priority, stack, &mThread);} else {res =androidCreateRawThreadEtc(_threadLoop,this, name, priority, stack, &mThread);} … }int Thread::_threadLoop(void* user){…do {…result= self->threadLoop();…if(result == false || self->mExitPending) {self->mThreadExitedCondition.broadcast();break;}}while(strong != 0);return 0;}

threadLoop是个虚函数,继承Thread的类需要自己去实现这个函数,实现方式为

void AudioFlinger::AsyncCallbackThread::onFirstRef(){ run("Offload Cbk", ANDROID_PRIORITY_URGENT_AUDIO);} bool AudioFlinger::AsyncCallbackThread::threadLoop(){while(!exitPending()) {…}returnfalse;}

这里exitPending是这么定义的

bool Thread::exitPending() const{returnmExitPending;}

所以,你可以选择在threadLoop里循环,也可以选择在_threadLoop里循环。

线程终止于run函数运行退出,要想退出一个线程,可以使用下面的接口:

1. 要求线程退出的线程不被block

void Thread::requestExit(){ mExitPending = true;}

2. 要求线程退出的线程被block,直到线程真正退出,注意self->mThreadExitedCondition.broadcast()出现在_threadLoop退出前夕

status_t Thread::requestExitAndWait(){mExitPending = true;while(mRunning == true) {mThreadExitedCondition.wait(mLock);} mExitPending = false;returnmStatus;}

看看具体的例子,,AudioFlinger中threadBase里的exit:

void AudioFlinger::ThreadBase::exit(){AutoMutex lock(mLock);requestExit();mWaitWorkCV.broadcast(); requestExitAndWait();}

在AudioFlinger析构的时候

AudioFlinger::~AudioFlinger(){…while(!mPlaybackThreads.isEmpty()) {closeOutput_nonvirtual(mPlaybackThreads.keyAt(0));}…}

函数closeOutput_nonvirtual内部调了thread->exit();

下面看看join:

status_t Thread::join(){ Mutex::Autolock _l(mLock);if (mThread== getThreadId()) {returnWOULD_BLOCK;}while(mRunning == true) {mThreadExitedCondition.wait(mLock);}returnmStatus;}

所以join是block调用join的线程,直到mThreadExitedCondition broadcast,也就是说,直到mThreadExitedCondition所属的线程退出。

比如T.join()意味着执行这句程序的线程被block,直到线程T推出

带时间参数的join表示最多只等待一段时间,过期不候。

其实你已经错过了旅行的意义。

Android Framework层线程设计

相关文章:

你感兴趣的文章:

标签云: