• 谈谈你对 Golang 调度模型的理解?


    什么是golang调度模型:

    golang调度模型即两级线程模型,是由G(goroutine)P(资源)M(工作线程,KSE绑定)三元素构成。M个G对N个M

    设计策略:

    复用线程 利用并行  抢占  全局G队列

    work stealing机制 hand off机制

    调度流程:(调度器模型图)

      每个M都包含一个g0(系统栈)和g(信号栈),这些称为系统g,M上其他的G则称为用户G。(go的角度)一个go func()创建,会首先加入P的本地可运行队列,P的可运行队列满了,就会导致P的本地队列的前半部分打乱顺序和先创建的G一起放入调度器的可运行队列。被M拿到后开始执行,销毁,然后开启新一轮调度帮助M获取其他的G。(如果此时G发生systemCall阻塞,此时M会锁定G,与当前的P解绑,唤醒或创建一个新的M,来绑定当前的P。等到这个G从系统调用退出时,判断是否可执行,可以继续执行,不行就放到调度器的可执行队列中)

    (全局的角度)(一系列初始化完成后,会开启第一轮调度,此时会首先执行含有main函数的go代码,然后就会到go的创建一系列流程。schedule()函数会先从M开始,1 如果发现当前M已经与G锁定,此时检测G的状态,不可运行就停止此轮调度,可运行就执行这个G 2 没有绑定G,检查是否执行串行运行时任务(垃圾回收中的子任务,panic任务),没有则继续 。检查是否存在执行追踪读取任务的G;检查是否有执行GC标记任务的G;检查计数器是否为61的倍数,是的话在调度器的G可运行队列获取;检查P的本地G可运行队列中是否有可运行的G,没有就会进行阻塞,执行findrunnable()方法;

    全力查找可运行G详细分为2个阶段10个步骤

    1 是否可以在执行终结器获取G 2是否可以在本地可运行队列获取G 3是否在全局G可运行队列获取G  4I/O轮训器中获取G 5 去其他P偷取 6 检查是否有GC标记的G 78910

    调度场景:

    创建一个M

    结束一个go

    解决了什么问题

    栈管理和抢占

    快,滋醒这个做梦的人,有糖尿病的往后靠靠哈,不要给他点甜头!
  • 相关阅读:
    bzoj3946
    bzoj3065
    bzoj1500
    bzoj1233
    bzoj1089
    bzoj1087
    bzoj1086
    if语句之猜拳
    if语句判断闰年、平年
    if语句判断身高体重是否标准
  • 原文地址:https://www.cnblogs.com/jianzhaojing/p/14654369.html
Copyright © 2020-2023  润新知