关于M的自旋和休眠

来源:1-4 Go 程序是怎么跑起来的

linxiaoyi

2021-06-23 21:26:58

①M有几种状态:

  • 自旋中(spinning): M正在从运行队列获取G, 这时候M会拥有一个P;

  • 执行go代码中: M正在执行go代码, 这时候M会拥有一个P;

  • 执行原生代码中: M正在执行原生代码或者阻塞的syscall, 这时M并不拥有P;

  • 休眠中: M发现无待运行的G时会进入休眠,并添加到空闲M链表中, 这时M并不拥有P。

第一点,工作线程M的自旋状态(spinning)工作线程在从其它工作线程的本地运行队列中盗取goroutine时的状态称为自旋状态。从上面代码可以看到,当前M在去其它p的运行队列盗取goroutine之前把spinning标志设置成了true,同时增加处于自旋状态的M的数量,而盗取结束之后则把spinning标志还原为false,同时减少处于自旋状态的M的数量,从后面的分析我们可以看到,当有空闲P又有goroutine需要运行的时候,这个处于自旋状态的M的数量决定了是否需要唤醒或者创建新的工作线程。

曹大,①中对自旋状态描述是不是不对,②中好像更细一些,我看源码好像不止在stealwork的时候有置为自旋状态。

1.这个自旋状态应该怎么理解呢?

2.M的G0执行schedule,如果找到可用的G,就切到G去继续走execute,然后exit结束再到G0走下一轮schedule。如果一直到findrunable结束都没找到是不是就进入休眠,不会再走schedule。这段我描述的对嘛?

写回答

1回答

Xargin

2021-06-25

我觉得也是 ② 的精确一些


1.这个自旋状态应该怎么理解呢?

我觉得这个自旋就是暂时还没找到 Goroutine 来执行,但是正在找的一个状态。。有这个状态和 nmsping 的计数,能够帮 runtime 判断是不是需要再启动额外的线程来执行 goroutine

2.M的G0执行schedule,如果找到可用的G,就切到G去继续走execute,然后exit结束再到G0走下一轮schedule。如果一直到findrunable结束都没找到是不是就进入休眠,不会再走schedule。这段我描述的对嘛?

就切到G去继续走execute,这句不对,从 g0 切换到用户 g 是在汇编函数 gogo 里做的

​其它几句没啥问题

1

Go高级工程师实战营

慕课网与 GoCN 社区官方联手打造,定义行业Go高级人才培养标准,4个月,快速晋升为P6+/D7级高级人才。

458 学习 · 266 问题

查看课程