OOM 杀进程 or 应用卡顿?该如何抉择

简介: 阿里云操作系统控制台推出了 FastOOM 功能,支持节点以及 Pod 级别的用户态 OOM 配置,通过提前介入杀进程的方式避 Near-OOM 导致的抖动夯机。

【阅读原文】戳:OOM 杀进程 or 应用卡顿?该如何抉择

 

背景

 

近期,大量用户反馈系统在运行过程中出现 CPU 利用率与系统负载(load)突发性飙升,甚至引发系统短时卡顿(持续数秒至数十秒)的问题;对于业务来说,轻则导致几百毫秒的抖动,重则连机器都无法ssh上去。经分析发现,此类异常现象普遍存在一个显著特征:均发生在系统内存占用率接近阈值(90%-95%)时。用户就发出了灵魂拷问:

 

“水位这么高了,为什么内核不触发 OOM 杀掉一些进程来释放内存?"

 

“我宁愿内核 OOM 把我业务进程杀了,我也不希望应用卡顿和系统夯机影响我其他业务!”

 

其实这个现象的核心原因就是:内核想确保应用实在没内存用了才 OOM

 

思想总体是正确的!但是一条思想要满足所有场景也是非常难的!

 

为什么还不 OOM ?!

 

内存水位这么高,为什么还不 OOM!其实主要是由于系统进入了 Near-OOM 状态。我们先回顾一下 Linux 的内存回收机制,如下图所示:

 

图/Linux内存水线

 

Linux 划分了 high、low、min 三个内存水线。当系统剩余内存低于 low 水线后,内核会唤醒 kswapd 进程会被唤醒开始进行异步的内存回收,此时对系统没什么影响;系统剩余内存低于 min 水线后,内核会阻塞要分配的内存进程尝试尽可能地回收所有可回收的内存(主要是文件缓存以及一些内核结构体缓存),回收的过程中可能涉及到将文件缓存写入磁盘或遍历一些内核结构体,从而导致系统负载飙高、应用被阻塞。如果能成功回收内存并满足申请需求则不触发 OOM;

 

更糟糕的是,系统可能进入一种 Near-OOM 的活锁状态,即内核一边在尝试回收文件缓存;但是应用运行过程中从磁盘加载代码段等行为也在不断产生文件缓存,那么就会使整个系统负载持续飙高,甚至发生夯机。

 

所以,内核 OOM 的策略在业务延时敏感的场景,还是太保守了!

 

那么如果我们希望宁愿 OOM 把我业务进程杀了,我也不希望应用卡顿和系统夯机影响我其他业务?还有什么办法呢?

 

 

 

新OOM方案

 

 

 

为了应对 Near-OOM 现象,核心就是“快” OOM,在内核还在犹豫要不要 OOM 的时候,我们就替他做出决定!目前业界已有的方案主要是通过用户态提前杀死相关进程来提前释放内存,比如应用较为广泛的是Facebook(Meta)推出的 oomd。oomd 目前已经集成于systemd中成为systemd-oomd,且从Ubuntu 22.04 开始集成于 Ubuntu 中。但是 oomd 方案存在以下问题:

 

与 cgroupV2 以及 Linux 内核的 PSI(Pressure Stall Information)特性深度绑定。但 cgroupV1 目前仍然是云计算中主流 cgroup 版本,且由于PSI功能有一定的性能开销,在大部分云计算场景中都是默认关闭的。

 

只支持以 cgroup 为粒度杀进程,配置 cgroup 级别的杀进程策略。

 

所以oomd在适用性和灵活性上仍有欠缺。

 

为了解决上述问题,阿里云操作系统控制台推出了 FastOOM 功能,支持节点以及 Pod 级别的用户态 OOM 配置,通过提前介入杀进程的方式避 Near-OOM导致的抖动夯机。

 

FastOOM 同样采取用户态提前杀进程的形式来避免系统进入 Near-OOM 状态,主要分为采集预测模块和 kill 模块:采集预测模块会从阿里云自研操作系统中读取内存压力相关的指标,通过统计学方法对 OOM 发生的概率进行实时预测并判定当前节点或 pod 是否达到相应的内存压力或即将进入 Near-OOM 状态。kill 模块会根据用户配置的杀进程策略,选取对应的进程杀死。

 

最终所有由 FastOOM 执行的 kill 操作事件都会上报到控制台中心端进行展示,让用户方便了解底层的实际操作(不用担心 FastOOM 偷偷杀死了其他进程)。

 

 

 

 

使用 FastOOM 避免

Near-OOM 系统夯机抖动

 

 

 

案例一:配置节点级别策略解决系统

Near-OOM 抖动夯机问题

 

客户遇到的问题

 

某汽车行业发现某实例上业务长时间无响应、登录实例也十分卡顿。通过监控发现客户实例使用的内存在某个时间点开始徒增,接近系统的总内存(即 available 非常低),但没有超过系统总内存。

 

 

 

通过 top 命令可以看到系统的 CPU sys 利用率和 iowait 利用率和系统负载都持续飙高,kswapd0 线程占用非常高的 CPU 进行内存回收。

 

 

通过操作系统控制台的系统概览可以看到,在发生OOM 夯(即处于 Near-OOM 状态)的同时,也发生了用户态收包延时,业务发生了抖动。

 

 

解决方案

 

通过配置开启节点级别的 FastOOM 功能,由于业务是实验较为敏感的业务,内存压力选择中,且设置业务程序(以 python 启动,进程名包含 python 子串)为避免被 OOM 进程且设置无关的日志程序优先杀死。

 

 

开启后,当节点内存水位处于 Near-OOM 状态时,用户态提前介入,根据配置杀死了如下进程,从而释放了部分内存避免系统进入了夯机状态。通过操作系统控制台的系统概览可以看到 FastOOM 介入的相关记录

 

如下图所示,由于 kube-rbac-proxy 和 node_exporter 等进程 oom_score_adj 被设置为接近 999,FastOOM 会匹配内核策略优先杀死这些进程,但是由于杀死这些进程后释放内存较小,仍处于 Near-OOM;因此 FastOOM 杀死了配置优先杀死的 logcollect 进程。

 

 

由于用户态及时介入杀死进程释放出内存,使系统避免进入了 Near-OOM 的抖动状态。

 

案例二:配置 Pod 级别策略解决

Pod 应用抖动夯机问题

 

客户遇到的问题

 

在 Kubernetes 环境中,我们是可以为 Pod 中的容器配置对应的内存限制的。和节点 OOM 同理,如果 Pod 中的内存使用接近限制时。内核也会尝试回收 Pod 中所有可回收内存,才触发 OOM,这时候也会导致 Pod 内业务进程的延时阻塞。

 

某大数据客户会部署一些延时敏感的业务 pod(即 pod 中运行了多个业务进程)。业务时不时会存在响应长尾延时,但是网络相关指标一切正常。

 

后面我们接手问题后,通过 Alibaba Cloud Linux OS自研指标(该指标反映容器由于内存回收阻塞的时长)发现,存在非常高的内存回收延时,且时间节点和抖动时间匹配:

 

 

推荐客户配置 Pod 级别的 FastOOM 后,通过提前杀死 Pod 中的相关内存占用进程,避免了内存回收延时的发生,抖动也不再出现。

 

解决方案

 

操作系统控制台提供较为灵活的 Pod 级别的 OOM 杀进程策略配置,可以灵活配置 Pod 中容器内发生 OOM 时,避免和优先杀死的进程。

 

假设在集群中通过名为 test-alinux 的 daemonset 在每一个节点部署了对应的 pod。

 

 

在操作系统控制台中设置 Pod 级别 FastOOM 策略:

为了匹配对应的 pod,pod 名称填写 test-alinux(正则表达式会匹配不同节点上的 test-alinux-xxx pod),命名空间为 default。

 

由于只是希望控制 OOM 时的杀进程策略,将内存压力级别设置为高,则触发用户态 OOM 的时机会近似于内核 OOM 的时机。

 

对于杀进程策略:配置优先杀死特定进程和避免杀死业务进程和 pod 中的 1 号进程,从而避免 pod 重启或影响业务,设置完成后下发至特定节点。

 

 

将配置下发到对应节点后,当 Pod 中容器内存使用超过容器 limit 后,发生 OOM;可以通过操作系统控制台系统概览看到 FastOOM 事件记录,可以看到FastOOM 根据策略杀死了对应的进程,也避免了特定进程被杀死。

 

 

总结

 

人无完人,内核的 OOM 其实也不是万能的。为了能尽可能的回收内存,内核在发生 OOM 前会阻塞申请内存的进程,并尝试回收内存,这对于延时敏感的业务的影响是非常大的;如果内存持续保持在接近 OOM的水位,还会进入 Near-OOM 的活锁状态导致整机夯机。阿里云操作系统控制台的 FastOOM 功能,通过相关指标,支持节点/容器/pod 级策略,可精准杀指定进程,轻松弥补了内核 OOM 带来的延时卡顿问题。

/END/


我们是阿里巴巴云计算和大数据技术幕后的核心技术输出者。

欢迎关注 “阿里云基础设施”同名微信微博知乎

获取关于我们的更多信息~

相关文章
|
22天前
|
存储 人工智能 弹性计算
WordPress AI助手操作
本文将介绍如何使用阿里云百炼平台创建知识库与AI助手应用,包括数据上传、模型配置、应用部署及资源清理等步骤,并详细说明了如何在Web页面集成AI助手悬浮框,实现智能对话功能。
146 5
|
22天前
|
Java 数据库 C++
Java异常处理机制:try-catch、throws与自定义异常
本文深入解析Java异常处理机制,涵盖异常分类、try-catch-finally使用、throw与throws区别、自定义异常及最佳实践,助你写出更健壮、清晰的代码,提升Java编程能力。
|
3月前
|
Kubernetes Cloud Native 安全
云原生机密计算新范式 PeerPods技术方案在阿里云上的落地和实践
PeerPods 技术价值已在阿里云实际场景中深度落地。
|
22天前
|
存储 消息中间件 人工智能
Lazada 如何用实时计算 Flink + Hologres 构建实时商品选品平台
本文整理自 Lazada Group EVP 及供应链技术负责人陈立群在 Flink Forward Asia 2025 新加坡实时分析专场的分享。作为东南亚领先的电商平台,Lazada 面临在六国管理数十亿商品 SKU 的挑战。为实现毫秒级数据驱动决策,Lazada 基于阿里云实时计算 Flink 和 Hologres 打造端到端实时商品选品平台,支撑日常运营与大促期间分钟级响应。本文深入解析该平台如何通过流式处理与实时分析技术重构电商数据架构,实现从“事后分析”到“事中调控”的跃迁。
257 55
Lazada 如何用实时计算 Flink + Hologres 构建实时商品选品平台
|
1月前
|
数据采集 边缘计算 缓存
从流量到留量:ESA 安全加速守护零售行业交易全链路
零售业正经历数字技术驱动的深度变革,电商蓬勃发展,消费持续升级。阿里云边缘云推出零售交易行业解决方案,通过分布式边缘计算、智能路由与安全防护,助力企业应对跨地域交易挑战,实现安全高效发展。
115 14
|
2月前
|
运维 监控 算法
小白也能做OS运维:阿里云操作系统控制台助你轻松解决三大运维难题
阿里云推出了一站式运维管理平台操作系统控制台,提出了异常告警和诊断联动的一套解决方案,对异常指标进行智能检测