写点什么

k8s 中无声的性能杀手:cpu thorttling(限流)

  • 2023-08-18
    北京
  • 本文字数:1197 字

    阅读完需:约 4 分钟

k8s 中,每个 pod 使用 cpu request 和 limit 来申请和管理实际使用的资源。


request 仅作用于分配期,limit 才是运行期时真正限制的指标。


例如:一个 poc,cpu_request : 2000mi,cpu_limit : 4000mi (1000mi 接近一个 cpu 时间片,4000mi 代表 4cpu)


k8s 使用 linux 的 cfs 调度器来完成对 limit 限制的调度,保证 pod 不会使用超过 limit 限制的 cpu 资源。


cfs 调度器每 100ms 调度一次,如果进程在前 50ms 就用光了在这 100ms 分配的 cpu 时间片,后 50ms 就没有 cpu 可用,需要等待到下一个调度周期,这个过程就是 cpu thorttling , 中文名称是 cpu 限流/节流。笔者倾向于叫 cpu 限流。


从这上面看,一切都正常,设定了 limit,那么就按照设定的 limit 来运行。


问题来自于这些地方,并且非常严重:


  1. linux kernel 的 cfs 有 bug,有一些不应该触发限流的场景,会触发限流。该问题在 k8s 的 repo 中有讨论,一部分 fix 合并到了 kernel 4.18 和 5.4 版本。但是依然有反馈还是存在会触发不必要的限流。#67577 #97445

  2. 使用 k8s 时,如果没有注意到 cpu thortlling 的监控,就会导致应用产生 cpu 限流,从而导致 rt 下降。一部分公司的私有云甚至根本不提供 cpu thorttling 监控。

  3. 信号堆叠问题,cfs 调度 100ms 一次,但是大多数监控都是分钟级别,少数能做到秒级,很难识别到 100ms 调度周期中 cpu limit usage 超过 100%的情况。大多数的表现是,cpu 使用率只有 25%-50%左右,但是应用性能却突然变差。

  4. 应用有突发流量翻倍/java 应用 gc 等场景,也都有可能导致 cpu 限流,从而影响性能。


k8s 中的 limit 目前在业界被认为是一个反模式,有 k8s 开发人员倾向于彻底取消 limit。但是没有其他可靠的配额限制手段时,取消 limit 还是太激进了。


cpu 限流的解决方案:


  1. 超额配置 limit,以保证突发 cpu 使用不会触发限流。该选项会导致资源浪费严重(因为高优先级 pod 的 limit=request),为了罕见情况超配资源。

  2. cpu brust , cpu brust 功能可以实现,如果 pod 平时的使用的 cpu 小于 limit,差值的部分就可以积累下来,在该 pod 使用 cpu 超标时,从积累部分扣除,从而保证整体的 cpu 使用率平滑。在阿里的测试中,启用该选项可以降低 33%的限流(33%-->0%),rt 从 111ms 降低到 71ms。

  3. 目前社区有在讨论在高优先级(request = limit)的 pod 中取消 cfs,因为它的资源是完全充足的,不需要通过 cfs 来限制。


以上这些解决方案,都依赖针对 cpu thorlling 的监控,有了监控才能知道有没有问题,实施了解决方案以后有没有改善。


如果使用私有云,而云部门没有提供相关监控的话,可以在容器中使用以下命令查看 cpu 限流情况。


cat /sys/fs/cgroup/cpu/cpu.stat
nr_periods 226 // 容器总运行周期nr_throttled 26 // 容器限流周期throttled_time 2117783298
复制代码


通过 nr_throttled / nr_periods 即可计算出限流率。


我们实际中的一个案例:cpu 密集型服务,cpu = 4c , 按分钟统计的 cpu 使用为 25%;流量:每小时会一次 qps 翻倍的情况。平均耗时为 12ms。调整 cpu=8c,平均耗时降低为 4ms.


cpu 最高使用率 60%,依然出现了很多 cpu 限流

发布于: 刚刚阅读数: 4
用户头像

公众号:摸鱼编程 学习事半功倍的编程技巧 2018-05-27 加入

我是小亢,现某大厂架构师,专注提供java、jvm、架构、finops领域知识。

评论

发布
暂无评论
k8s中无声的性能杀手:cpu thorttling(限流)_k8s_你头顶的那片星空_InfoQ写作社区