博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Chrome多线程模型
阅读量:5290 次
发布时间:2019-06-14

本文共 1715 字,大约阅读时间需要 5 分钟。

  • 为什么使用多线程?
  • Chrome的多线程模型主要解决什么问题?
  • 如何实现该问题的解决?


1. 解决问题

Chrome有很多线程,这是为了保持UI线程(主线程)的高响应度,防止被其他费时的操作阻碍从而影响用户体验。但是多线程会造成资源并发访问引起的死锁和竞争冲突等问题。

2.方法

Chrome的多线程模型为避免资源被并发访问,尽量减少锁的使用,通过消息循环和自定义任务机制解决了并发问题。对于任一个线程,都是启动一个消息循环,等待和执行消息队列中的消息或任务。Chrome将需要的操作封装入自定义的任务Task中,由任务派发机制将Task传递给相应线程去执行,也只有在Task加入任务队列时需要加锁。线程之间数据传递也是通过封装Task进行通信。

3. 消息循环

Chrome中的主要线程根据其负责事务分为三类:

  • 普通线程:只能执行Task,没有其他的功能。
  • UI线程(也叫chrome线程):所有的窗口都需要跑在UI线程上,它除了能执行Task以外,还能执行和界面相关(UI)的消息循环。
  • IO线程:和本地文件读写,或者网络收发相关的操作都运行在这个线程上,它除了能执行Task以外,还能执行和IO操作相关的事件回调。

结构:这三种线程处理的消息也可以相应分为三类:只处理Task,处理Task和UI消息,处理Task和IO消息。分别定义三个类来实现对消息的处理。其中MessageLoop作为基类处理Task,由它派生出来的两个类MessageLoopforUI和MessageLoopforIO分别处理另外两种消息类型以及相关平台信息(UI消息和IO操作是平台相关的)。为了结构清晰,定义一个新的基类及其子类来负责处理消息,这就是MessagePump。MessagePump的每个子类针对不同平台和不同的消息类型。事实上,不仅如此,消息处理的主循环也在MessagePump中。因此,MessageLoop通过实现MessagePumpDelegate的接口来负责处理自定义任务。

过程:消息处理的主循环在MessagePump中。消息循环开始,通过RunLoop接口调用MessageLoop,MessageLoop通过MessagePumpDelegate(消息代表)调用MessagePump,从MessagePump开始处理消息,对工作队列中的任务,根据其优先级分别执行(Work,DelayWork,IdleWork),处理完后判断是否还有待处理的任务,有则继续新一轮循环,无则暂停等待唤醒。(消息等待:对于IO消息等有OS提供支持,对于自定义的Task,则通过建立管道,在Task到来时写入一个字节从而唤醒消息循环?)

*待修改

【未整理】延时任务(延迟延迟任务队列和需在顶层执行的延迟任务队列),输入队列和工作队列(任务复制)

4. Task

为了统一所有消息循环中的任务调用方式,所有的任务的基类都是这个Task类,他唯一的方法就是run(),MessageLoop只需要调用这个虚函数即可。如果为了简化开发,光是一个Task,就提供了各式各样的派生类。

  • 它提供了一大套的模板封装(参见task.h),可以将Task摆脱继承结构、函数名、函数参数等限制。
  • 派生出来的Task有:CancalableTask,ReleaseTask,QuitTask等等。
  • 在消息循环中,根据不同的应用场景,将Task又分为即时处理的Task、延时处理的Task和Idle时处理的Task。
  • 为了简化开发,还引入了RunnableMethod,封装对象的方法,减少我们自己实现Task的时间。
  • 调用PostTask时,还需要传入一个tracked_objects::Tracked,Tracked是为了实现多线程环境下
    的日志记录、统计等功能,用于追踪Task的产生位置,为调试做准备,使得Task天生就有良好的可调试性和可统计性。

【未整理】Task在线程内创建,执行,抛出,加入,复制,销毁,…,的实现;

5.参考资料

转载于:https://www.cnblogs.com/amonian/p/3372818.html

你可能感兴趣的文章
IOS开发基础知识--碎片25
查看>>
对比传统的Xilinx AMP方案和OPENAMP方案-xapp1078和ug1186
查看>>
面试题2
查看>>
selenium+java iframe定位
查看>>
js基础
查看>>
Js函数初学者练习(一)switch-case结构实现计算器。
查看>>
P2P综述
查看>>
细读 php json数据和JavaScript json数据
查看>>
第五章 如何使用Burp Target
查看>>
Sprint阶段测试评分总结
查看>>
Servlet3.0新特性
查看>>
java内存溢出怎么解决
查看>>
JS对象以及"继承"
查看>>
Ewebeditor最新漏洞及漏洞大全
查看>>
socket计划编制的原则
查看>>
sqlite3经常使用命令&语法
查看>>
[leetcode] 309. Best Time to Buy and Sell Stock with Cooldown(medium)
查看>>
解决微信授权回调页面域名只能设置一个的问题 [php]
查看>>
数组去重一步到位
查看>>
HDU 4671 Backup Plan 构造
查看>>