Chinaunix首页 | 论坛 | 博客
  • 博客访问: 318899
  • 博文数量: 88
  • 博客积分: 2051
  • 博客等级: 大尉
  • 技术积分: 950
  • 用 户 组: 普通用户
  • 注册时间: 2008-04-14 23:59
文章分类

全部博文(88)

文章存档

2012年(3)

2011年(2)

2010年(9)

2009年(14)

2008年(60)

我的朋友

分类: C/C++

2008-10-12 17:59:21

symbian os kernel在NThread的基础上构建DThread为应用程序提供线程模型。Symbian OS thread有这些能力:
1.访问kernel function的能力
2.有一个异常处理器,允许kernel对在用户模式下产生的异常进行处理(通常是由于程序错误引起的),  symbian构建了一个稳健的应用处理程序的运行环境。
3.exit handler,允许线程退出时可以清理资源和通知线程结束。
 
每个symbian os thread都有两个stack,一个在用户模式下使用,一个是NThread在超级模式下使用。有了超级模式下的stack,这样当你的应用程序处在超级模式下运行时,只要NThread不是在critical section期间或者拥有fast mutex时,就可以中断!  中断时,就会把运行环境保护在stack里面!  
wow! is it right?
 
创建线程
1.DThread::Create(SThreadCreateInfo& aInfo)  创建DThread对象时,其状态是ECreated完全创建好过后才是EReady。首先分配stack,然后调用NKern::ThreadCreate()创建nanokernel thread;从这个函数返回后,就把DThread添加到object container当中去。 如果该线程是一个user thread,就会把创建的信息copy到user stack中去,如果有必要为这个线程创建独立的heap;最后,如果这个线程是主线程,在调用E32Main()之前,要调用所有static data的构造函数;如果不是主线程,直接调用线程的入口函数。
 
2.线程的同步
Symbian os kernel提供DSemaphore支持多个线程同时wait,并按照优先级释放对应线程;提供DMutex支持嵌套,一个线程可以同时hold多个mutex,也可以多次hold同一个mutex。 mutex支持优先级继承的特性,比如一个线程A的优先级很低,已经hold了一个mutex,一个线程B优先级更高,wait在mutex上,那么线程A的优先级就会调高到B的程度,知道release掉这个mutex,回归原来的优先级。 所以,线程的优先级在内核调度看来,是在不断变化的。
系统通过system lock来支持对semaphore和mutex的操作。因为,他们本身也需要锁!
之所以,semaphore和mutex效率比while高,因为它们都是内核对象;内核根据这些对象的属性来调度thread。
为了让wait在一个mutex上的最高优先级的线程最先获得该mutex,需要做到:a。将获得mutex的操作延迟到最后一刻!  对mutex的释放操作是先释放mutex,然后release最高级的线程;如果它能获得这个mutex,它就可以继续运行!b。对所有wait的线程排序,并release第一个线程!c。具有优先级继承性!d。区别对待EWaitMutex和EWaitMutexSuspend状态。
 
关于symbian中的条件变量!DCondVar
条件变量通过Mutex来实现,当满足一定条件时,才会block线程。例如,当buffer满时,就要阻塞生产者线程继续生产。对这个条件的测试,是一段critical section,通过这个条件变量的mutex保护起来。
 
在消费者线程的场景中,cosumer
 
 

mutex.Wait();
while(!CONDITION)
  condvar.Wait(&mutex);
cosume the data...
mutex.Signal();

关键就是condvar.Wait(&mutex)这个函数;它先release这个mutex,这样生产者线程可以向buffer里放数据;然后blcok这个线程,等待生产者线程唤醒;唤醒后,还在Wait函数中没有返回,Wait再一次mutex.wait(),获得对buffer进行操作的权利;然后测试条件,条件满足就处理data,否则继续循环。

那么这个唤醒功能是如何实现的呢? 生产者线程通过调用DCondVar的Signal或者Broadcast来唤醒所有阻塞在该条件变量上的线程。DCondVar有一个成员变量来记录所有等待在该条件变量上的线程。TThreadWaitList iWaitQ;

3.线程的退出

包括两个阶段:

a、恢复线程回到正常的状态,如跟mutex和semaphore断绝关系

b、运行thread-exit handler

c、完成logons

最后的一些工作必须在超级模式下完成,

 So the kernel performs a second phase of exit processing in
the supervisor thread context. Each DThread has a DFC, given by
iKillDfc, which is queued on the supervisor thread just before the
exiting thread actually terminates. The DFC completes the cleanup process
– closing thread handles, freeing stacks and freeing the thread control
block. If this is the last thread in a process, then it also closes process handles and frees the process control block.

阅读(649) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~