字体:大 中 小
护眼
关灯
上一章
目录
下一章
第687章 看不见的沙漏!
第(3/3)页
统。
日积月累。
这些被“遗忘”的,无法被再次使用的内存,就像血管里的血栓,会一点一点地,堵死整个系统。
“我们在哪里泄漏了内存?”黄建功喃喃自语。
他开始疯狂地,在脑中,回顾“天枢”V0.3的每一行业务逻辑。
创建任务时,分配TCB,分配堆栈。
这都是一次性的。
之后,系统就在五个任务之间,不断地切换,调度。
切换……调度……
每一次切换,内核都需要保存当前任务的上下文……
每一次调度,内核都需要测量切换的成本,计算新的时间片……
这个过程,会产生新的内存分配吗?
黄建功的目光,猛地落在了那段关于“上下文切换成本”的日志上。
`Switch cost: 12 us.`
`Switch cost: 15 us.`
`Switch cost: 73 us.`
为了计算这个成本,内核需要在切换前后,两次读取HPET的计数值。
然后,进行一次减法运算。
为了存储这两个计数值,和那个最终的差值,内核需要……临时的变量!
而这些临时变量,是存放在……
“堆栈里!”钱学敏和黄建功,几乎在同一时刻,失声喊了出来!
他们瞬间,就定位到了那个“看不见的沙漏”,到底藏在哪里!
每一次!
每一次时间中断发生时,CPU都会将当前任务的执行现场,压入内核的堆栈。
然后,跳转到中断服务程序。
中断服务程序,也就是他们的调度器,为了计算切换成本,又在内核堆栈上,定义了几个临时的变量。
当调度完成,切换到下一个用户任务时。
那些被中断压入的用户任务现场,会被正确地弹出。
但是!
他们忘了!
他们忘了去“清理”,那些在中断服务程序中,使用过的,临时的,属于内核自己的,堆栈空间!
每一次中断,内核的堆栈指针,都会因为这些被遗忘的临时变量,而向下,移动那么微不足道的,几个字节。
一次中断,几个字节。
一秒钟,一百次中断,就是几百个字节。
三十分钟……
黄建功的心,凉了半截。
他终于明白,那4MB的内存,是怎么被一点一点,耗光的了。
不是用户任务的错。
也不是内存管理器的错。
是他们自己!
是他们亲手编写的,那个被他们视为“绝对公平”的调度器,在每一次“心跳”的时候,都在为自己,挖深一点点的,坟墓!
记住手机版网址:m.lewenwx.cc
上一章
目录
下一章