[note/golang]GopherCon 2018 - Golang调度器/GMP笔记

调度对象——Goroutine

  • Goroutine是用户空间线程 (完全由Go运行时管理,没有OS介入)
  • 轻量,开销小(更小的内存开销,更快的创建、销毁,上下文切换)

参考对比
在这里插入图片描述

为什么需要调度器?

由于Goroutine是用户层面的抽象,操作系统只认识内核线程。需要Go 调度器将多个 Goroutine 映射到实际的内核线程上。

对应会需要完成两项工作——Goroutine分发和创建线程。
在这里插入图片描述

Go 调度器的设计目标

  • 使用少量的内核线程: 创建内核线程代价高昂,因此调度器力求高效地复用内核线程。
  • 支持高并发: Go 程序会涉及大量的 Goroutine,调度器需要满足这种需求。
  • 利用并行性: 原则上在N核机器上,Go程序应能够并行N个Goroutine。

何时进行调度?

操作可能影响 Goroutine 执行时,Go 调度器就会介入
在这里插入图片描述

  • Goroutine 创建
  • Goroutine 阻塞: 如等待channel或mutex
  • 系统调用: 阻塞的系统调用同时会阻塞内核线程

Go 调度器关键思想

  • 运行队列(runqueue): 等待运行的 Goroutine 被放置在队列中。最初,使用的是单个全局队列,但在多线程情况下会导致竞争问题。解决方案是分布式运行队列,每个线程都获取自己的队列。
  • 线程复用: 空闲线程不进行销毁,会被用在检查全局运行队列、网络轮询、尝试运行gc任务、工作窃取上,如果仍然空闲会放置在一个链表中等待复用,以期最大利用并行性。
  • GOMAXPROCS:限制正在运行Goroutine的线程数为CPU逻辑核心数。
  • 工作窃取(work-stealing): 如果一个线程的本地运行队列为空,它可以随机“窃取”其他线程队列中一半的任务,平衡线程之间的工作负载。
  • 移交(hand-off): 当一个线程被阻塞(例如,由于系统调用)超过一段时间时,它关联的运行队列会由“sysmon”转交到另一个线程,此时唤醒(Unpark)可复用的线程,如果需要的话创建新线程(线程数限制只适用于正在运行Goroutine的线程),防止 Goroutine 饥饿。
  • 协作式抢占: Go 调度时间节点依赖于程序自发调用调度器。但如果一个 Goroutine 长时间占用 CPU 不放,会由“sysmon”后台线程检测到(>10ms运行,警告)在可能的情况下抢占并将其放置于全局运行队列,确保公平性并防止饥饿。
  • 全局运行队列: 全局运行队列充当被抢占的 Goroutine 的低优先级队列。
  • “sysmon”线程:检测长时间运行的Goroutine,移交运行队列。

Go 调度过程示例

请添加图片描述

局限性

  • 没有 Goroutine 优先级: 所有 goroutine 都被平等对待,这在某些任务需要更高优先级的情况下可能会出现问题。
  • 没有强抢占: 协作式抢占无法保证公平性或延迟。

(后续有引入,参见https://stackoverflow.com/questions/73915144/why-is-go-considered-partially-preemptive)

  • 对硬件拓扑的感知有限: 调度器目前缺乏对底层硬件拓扑的感知,局部性利用程度不高。

参考资料与扩展阅读

  • https://www.youtube.com/watch?v=YHRO5WQGh0k (*) 参考talk
  • https://speakerdeck.com/kavya719/the-scheduler-saga (*) 参考slices
  • https://www.youtube.com/watch?v=wQpC99Xu1U4 强抢占的引入
  • https://mukeshpilaniya.github.io/posts/Go-Schedular/
  • 18
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值