上文对Chromium中多线程机制做了简要说明,下面从代码上加以分析。
Chromium多线程机制的实现可以说堪称经典,可以为我们好好学习和模仿。
每一个线程中包含有一个MessageLoop,MessageLoop实际上可以看作是任务的队列,线程就是不停的从MessageLoop中选择任务投入运行。一个任务运行完毕后,再从队列上选择下一个任务投入运行,直到队列上没有任务为止,然后线程处于休眠状态,等待新的任务加入。
这里所说的新的任务可以是在本线程中添加的,当然也可以是其他线程推送过来的。在线程之间相互添加任务时,Chromium的代码里是通过BrowserThread类的静态函数PostTask或PostDelayedTask完成的。这样可以实时获取每个线程的MessageLoop,每个线程都不会保存其他线程的MessageLoop指针,因为那样做会带来潜在的Bug,例如保存的MessageLoop指针可能由于线程的终止而被销毁了。
例如:BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE, base::Bind(&WriteToFile, "foo.txt", "helloworld!"));
就是把任务WriteToFile发送到File线程中去执行,本线程可以是File线程,亦可以是UI或其他线程。多线程编程最复杂的部分应该是多个线程之间数据的同步,而在Chromium的多线程设计中只需要在添加或提取任务时对MessageLoop队列数据同步,对MessageLoop操作加锁即可,这大大简化了多线程间任务的同步,减少了任务运行期间不必要的等待。