ImageVerifierCode 换一换
格式:DOCX , 页数:10 ,大小:19.68KB ,
资源ID:3693976      下载积分:3 金币
快捷下载
登录下载
邮箱/手机:
温馨提示:
快捷下载时,用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)。 如填写123,账号就是123,密码也是123。
特别说明:
请自助下载,系统不会自动发送文件的哦; 如果您已付费,想二次下载,请登录后访问:我的下载记录
支付方式: 支付宝    微信支付   
验证码:   换一换

加入VIP,免费下载
 

温馨提示:由于个人手机设置不同,如果发现不能下载,请复制以下地址【https://www.bdocx.com/down/3693976.html】到电脑端继续下载(重复下载不扣费)。

已注册用户请登录:
账号:
密码:
验证码:   换一换
  忘记密码?
三方登录: 微信登录   QQ登录  

下载须知

1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。
2: 试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
3: 文件的所有权益归上传用户所有。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 本站仅提供交流平台,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

版权提示 | 免责声明

本文(MTK task相关.docx)为本站会员(b****4)主动上传,冰豆网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知冰豆网(发送邮件至service@bdocx.com或直接QQ联系客服),我们立即给予删除!

MTK task相关.docx

1、MTK task相关MTK Task相关 MTK 的 基本执行单元是task,从操作系统的角度来理解,task 有些像线程而不是进程,进程之间的地址空间是相互隔离的,说白点就是进程之间的全局变量是不相互干扰的,而线程之间则是用同一个地址空间,MTK 的task 之间的地址空间也是共同的,也就是在MTK 编程里,定义了一个全局变量,那么在任何一个task里面都能引用,(这里举个例子,在实际编程过程中最好不要用全局变量,实在没有办法避开,那么全局变量也要分模块化,进行封装, 扯远了)。所以说,MTK 的task 更像线程,MTK 用的是实时操作系统 nucleus,是非抢占式操作系统,也就是当高优

2、先级的task 在运行时,底优先级的task是得不到运行时间的,除非等高优先级的task 因为种种原因挂起。MTK 还有一个跟task 想关的概念 叫 module,它跟task 之间的关系是:一个task 可以对应多个module。task 主要表示是一个执行单元,module 主要是用于传递消息,在MTK 中,消息传递是module 为单位 src_mod des_mod,而不是以task为单位。虽然MTK手机,是feature phone(功能机),不像symbian 6 那样可以同时运行多个应用。但是MTK还是 有许多task组成。平时MTK的后台播放MP3就是一由一个task 完成的

3、。具体以后分析。现在来看看MTK 最主要的task,MMI task,MTK 的应用程序都是在该task里面运行,它有一整套开发MTK 应用的framework。先来看创建MMI task的函数kal_bool mmi_create(comptask_handler_struct *handle)/*-*/* Local Variables */*-*/static comptask_handler_struct mmi_handler_info =MMI_task, /* task entry function */MMI_Init, /* task initialization funct

4、ion */NULL,NULL, /* task reset handler */NULL, /* task termination handler */;/*-*/* Code Body */*-*/*handle = &mmi_handler_info;return KAL_TRUE;这个函数的结构,是MTK 创建task的基本结构,系统初始化时,会调用该函数。看里面的结构体typedef struct kal_task_func_ptr comp_entry_func; /task 的入口函数task_init_func_ptr comp_init_func; /task 的初始化函数t

5、ask_cfg_func_ptr comp_cfg_func; /task 的配置函数task_reset_func_ptr comp_reset_func; /task 的重置函数task_end_func_ptr comp_end_func; /task 的终止函数 comptask_handler_struct;task 的入口函数是必须的,这个函数告诉系统,初始化完相应的task 控制块后,就要进入该函数来运行。task 初始化函数,是在进入 task 入口函数之前被调用,用来初始化可能需要的资源,可选。task 终止函数是,当task 结束是要调用,用来释放资源,可选。其他两个函数我

6、也不清楚干什么,希望知道的共享下先看MMI task 的初始化函数.MMI_BOOL MMI_Init(task_indx_type task_indx)/创建一个mutex(互斥体)mmi_mutex_trace = kal_create_mutex(mmi_trace);/这个是初始化 2step 按键, 2step 按键是指 有一些按键具有半按下状态/比如照相功能,按下一半进行聚焦,再按下一半拍照mmi_frm_get_2step_keys();/初始化timer,具体可以看 MTK timer 小结 系列L4InitTimer();/初始化 UI 相关信息,里面有许多画点,图等函数se

7、tup_UI_wrappers();return MMI_TRUE;初始化函数比较简单。下面来看MMI 的入口函数,这个函数是整个MMI 运行的核心。/为了简单,删除了大部分宏控制程序void MMI_task(oslEntryType *entry_param)MYQUEUE Message;oslMsgqid qid;U32 my_index;U32 count = 0;U32 queue_node_number = 0;/ 获得task的外部消息队列id,通过这个id,获得别的task 往MMI task发送的消息/ MMI task 有两个消息,外部消息队列和内部消息队列/ 外部消息队

8、列的消息不直接处理,只是简单的存放到内部消息队列,/ 这样使内部消息队列的优先级稍微高一点qid = task_info_gentry_param-task_indx.task_ext_qid;mmi_ext_qid = qid;/ 初始化 event 处理函数,这个几个event 必须在获得消息前就进行注册/ 不让可能使得这个event 丢弃。具体event 事件,下次介绍InitEventHandlersBeforePowerOn();/进入task 的while 循环/ task 的while(1) 循环使得这个task 不会结束,只有挂起或者运行while (1)/ 判断是否有 key

9、 事件需要处理if (g_keypad_flag = MMI_TRUE)mmi_frm_key_handle(NULL);/ 获得外部消息队列里,消息的个数msg_get_ext_queue_info(mmi_ext_qid, &queue_node_number);/ 如果没有任何消息需要处理(内部消息和外部消息都没有,同时也没有按键需要处理)/ OslNumOfCircularQMsgs 获得内部消息队列消息的个数if (queue_node_number = 0) & (OslNumOfCircularQMsgs() = 0) & (g_keypad_flag = MMI_FALSE)U

10、8 flag = 0;ilm_struct ilm_ptr;/去外部消息队列里获得消息,这是一个阻塞函数,也就是说,如果外部消息队列里,/没有任何消息,那么这个task 将被阻塞,或者说挂起,也就是不在运行,/直到有消息到达,才会被唤醒, 看过操作系统原理的,应该不难理解这个意思和这个本质OslReceiveMsgExtQ(qid, &Message);/如果有消息,获得task 的indexOslGetMyTaskIndex(&my_index);/ 设置该task的获得mod 为MMI mod.OslStackSetActiveModuleID(my_index, MOD_MMI);/保存

11、该消息,用于放入到内部队列ilm_ptr.src_mod_id = Message.src_mod_id;ilm_ptr.dest_mod_id = Message.dest_mod_id;ilm_ptr.msg_id = Message.msg_id;ilm_ptr.sap_id = Message.sap_id;ilm_ptr.local_para_ptr = Message.local_para_ptr;ilm_ptr.peer_buff_ptr = Message.peer_buff_ptr;/放入内部队列/ 这个内部队列是个简单的循环队列flag = OslWriteCircular

12、Q(&ilm_ptr);/ 对 timer 消息进行特殊处理if (Message.src_mod_id != MOD_TIMER)hold_local_para(ilm_ptr.local_para_ptr);hold_peer_buff(ilm_ptr.peer_buff_ptr);OslFreeInterTaskMsg(&Message);else/ 把外部消息放入到内部消息mmi_frm_fetch_msg_from_extQ_to_circularQ();/处理内部消息count = OslNumOfCircularQMsgs();while (count 0)OslGetMyTas

13、kIndex(&my_index);OslStackSetActiveModuleID(my_index, MOD_MMI);if (OslReadCircularQ(&Message)CheckAndPrintMsgId(U16) (Message.msg_id);/是否是 wap 的消息/ 这里就体现了一个task 可以对应多个modif (Message.dest_mod_id = MOD_WAP)elseswitch (Message.msg_id)/timer 消息 具体看 MTK timer 小结 2case MSG_ID_TIMER_EXPIRY:kal_uint16 msg_l

14、en;/处理stack timer消息EvshedMMITimerHandler(get_local_para_ptr(Message.oslDataPtr, &msg_len);break;/开机消息/具体分析 见后文case MSG_ID_MMI_EQ_POWER_ON_IND:mmi_eq_power_on_ind_struct *p = (mmi_eq_power_on_ind_struct*) Message.oslDataPtr;/* To initialize data/time */SetDateTime(void*)&(p-rtc_time);gdi_init();g_pwr

15、_context.PowerOnMMIStatus = MMI_POWER_ON_INDICATION;switch (p-poweron_mode)case POWER_ON_KEYPAD:OslMemoryStart(MMI_TRUE);g_charbat_context.PowerOnCharger = 0;g_pwr_context.PowerOnMode = POWER_ON_KEYPAD;DTGetRTCTime(&StartUpTime);memset(&LastDuration, 0, sizeof(LastDuration);mmi_bootup_entry_disk_che

16、ck();break;case POWER_ON_PRECHARGE:case POWER_ON_CHARGER_IN:g_pwr_context.PowerOnMode = p-poweron_mode;InitializeChargingScr();if (!g_charbat_context.isChargerConnected)QuitSystemOperation();break;case POWER_ON_ALARM:g_pwr_context.PowerOnMode = POWER_ON_ALARM;gdi_layer_clear(GDI_COLOR_BLACK);AlmInit

17、RTCPwron();break;case POWER_ON_EXCEPTION:g_pwr_context.PowerOnMode = POWER_ON_EXCEPTION;gdi_layer_clear(GDI_COLOR_BLACK);OslMemoryStart(MMI_TRUE);SetAbnormalReset();InitializeAll();OslDumpDataInFile();ClearInputEventHandler(MMI_DEVICE_ALL);ClearKeyHandler(KEY_END, KEY_LONG_PRESS);InitNvramData();Ini

18、tAllApplications();mmi_pwron_exception_check_display();break;default:break;break;/ event 时间,这个也是MMI task 的一个重点default:ProtocolEventHandler(U16) Message.oslMsgId,(void*)Message.oslDataPtr,(int)Message.oslSrcId,(void*)&Message);break;OslFreeInterTaskMsg(&Message);msg_get_ext_queue_info(mmi_ext_qid, &q

19、ueue_node_number);count-;MMI task 的工作方式:从外部队列获取消息放入内部消息队列,内部消息队列根据消息类型注册的回调函数,进行调用(event 机制,这个又是MMI framework的主要部分之一)。在MTK上,用户(开发人员)可以根据需要,创建task。创建一个task 分为 4 步:1 增加一个task index 到 custom_task_indx_type2 增加一个mod index 到 custom_module_type3 把mod 关联到 相应的 task上,因为一个task 可以对应多个mod,所以需要把mod 挂载到 task上。(用挂

20、载这个词,应该就比较好理解了,task 是MTK 执行的基本单位,所以一个mod 要能独立运行,就要挂载到某个task 上,为什么不一个mod一个task呢,我想task越多,多系统效率影响就越大。那么就可以考虑互斥的mod 挂载到一个task上,反正互斥的,不会同时需要运行,就像音乐,视频,照相机一样,不会同时运行)4 创建 task 基本信息 到 custom_comp_config_tbl下面来具体看一个例子。1 添加 task indextypedef enum INDX_CUSTOM1 = RPS_CUSTOM_TASKS_BEGIN,INDX_CUSTOM2,#ifdef TASK

21、_CREATE_TESTINDX_TASK_TEST,#endifRPS_CUSTOM_TASKS_END custom_task_indx_type;我们增加了一个 task index INDX_TASK_TEST2 添加一个 mod indextypedef enum MOD_CUSTOM1 = MOD_CUSTOM_BEGIN,MOD_CUSTOM2,#ifdef TASK_CREATE_TESTMOD_TASK_TEST,#endifMOD_CUSTOM_END custom_module_type;我们增加了一个mod index MOD_TASK_TEST3 挂载mod 到 ta

22、sk上custom_task_indx_type custom_mod_task_g MAX_CUSTOM_MODS =INDX_CUSTOM1, /* MOD_CUSTOM1 */INDX_CUSTOM2, /* MOD_CUSTOM2 */#ifdef TASK_CREATE_TESTINDX_TASK_TEST,#endifINDX_NIL /* Please end with INDX_NIL element */;这样就把 MOD_TASK_TEST 挂载到 INDX_TASK_TEST上面了,这里的映射关系是通过index 来控制的,也就是说要的到MOD_TASK_TEST 对应的

23、 task index,只要这样 task index = custom_mod_task_gMOD_TASK_TEST; ,所以创建过程中,顺序一定要对应好,不然容易出错。4 创建task 信息const comptask_info_struct custom_comp_config_tbl MAX_CUSTOM_TASKS =/* INDX_CUSTOM1 */CUST1, CUST1 Q, 210, 1024, 10, 0,#ifdef CUSTOM1_EXISTcustom1_create, KAL_FALSE#elseNULL, KAL_FALSE#endif,/* INDX_CUS

24、TOM2 */CUST2, CUST2 Q, 211, 1024, 10, 0,#ifdef CUSTOM2_EXISTcustom2_create, KAL_FALSE#elseNULL, KAL_FALSE#endif,#ifdef TASK_CREATE_TEST/* INDX_TASK_TEST */TAST_TEST, TASK_TEST Q, 212, 1024, 10, 0,task_test_create, KAL_FALSE,#endif;这样就创建好了task 的信息,这里说task 需要的信息typedef struct kal_char *comp_name_ptr;

25、/task 的namekal_char *comp_qname_ptr; /外部队列namekal_uint32 comp_priority; /优先级kal_uint16 comp_stack_size; /stack 大小kal_uint8 comp_ext_qsize; /外部队列大小kal_uint8 comp_int_qsize; /内部队列大小kal_create_func_ptr comp_create_func; /task 创建函数kal_bool comp_internal_ram_stack; /是否是internal_ram_stack comptask_info_struct;task 的优先级是数值越大,优先级越低。由于是MTK 用的是实时操作系统,高优先级的task 只要需要,就会先运行,一直运行,所以task的优先级定义时需要考虑清楚。comp_internal_ram_stack 表示是否使用internal ram stack,internal ram 相对速度要快,但是数量很有限,一般自己创建的不要去使用,容易引起问题。

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1