Low memory killer参数如何优化?

99ANYc3cd6
预计阅读时长 13 分钟
位置: 首页 参数 正文

什么是 Low Memory Killer (LMK)?

Low Memory Killer 是 Android 内核(基于 Linux 内核)中的一个核心内存管理机制,当系统内存即将耗尽时,LMK 会被触发,它会根据一套预设的规则和优先级,强制杀死一些后台进程,以释放内存,确保前台正在运行的 Activity 和关键服务能够继续稳定运行,从而防止系统因内存不足而崩溃。

low memory killer参数
(图片来源网络,侵删)

LMK Android 系统的“内存保镖”,在内存紧张时“牺牲”一些进程来保全大局。


LMK 的核心参数

LMK 的行为主要由一组内核参数控制,这些参数通常位于 /sys/module/lowmemorykiller/parameters/ 目录下,最重要的参数是 adjminfree

minfree 参数

  • 作用:定义了内存的“警戒线”,它是一个由逗号分隔的数值列表,每个值对应一个内存阈值(单位通常是 KB)。
  • 工作原理:当系统可用内存下降到 minfree 列表中的某个阈值时,LMK 就会开始考虑杀死进程。
  • 列表长度minfree 列表的长度必须与 adj 列表的长度完全相同,通常在 Android 中,这个长度是 6,对应 6 个不同的进程优先级等级。

adj 参数

  • 作用:定义了进程的“可杀性”等级,它也是一个由逗号分隔的整数值列表,每个值对应一个 OOM (Out-Of-Memory) score。
  • 工作原理
    • 数值越小:表示进程的优先级越高,越不容易被杀死。
    • 数值越大:表示进程的优先级越低,越容易被杀死。
  • minfree 的对应关系adjminfree 是一一对应的。minfree 的第 N 个阈值和 adj 的第 N 个等级配对,当系统内存低于第 N 个阈值时,系统会优先杀死 adj 值大于或等于第 N 个等级的进程。

进程优先级等级 (adj 值)

Android 系统将进程分为几个明确的优先级等级,每个等级都有一个对应的 adj 值,理解这些等级是理解 LMK 的关键。

OOM Adjustment (adj) 进程优先级等级 描述 示例
-1000 不可杀 最优先级,绝对不能被杀死,通常是系统关键进程。 zygote, surfaceflinger
-900 前台可见进程 通常是当前可见的 Activity (如对话框) 或系统 UI。 一个显示在屏幕上的 App
800 不可见的前台进程 失去焦点但仍可见的进程 (如分屏模式下的另一个 App)。 处于分屏或画中画模式的 App
700 主服务进程 正在运行的服务进程 (如音乐播放服务、下载服务)。 正在播放音乐的音乐 App
600 可见的进程 包含一个可见的 Activity,但不在前台 (如被一个全屏对话框遮挡)。 被系统弹窗遮挡的 App
500 次要服务进程 包含一个已启动的服务,但不属于前几类。 后台运行的服务
400 缓存进程 可被杀死的进程,当内存极度紧张时,首先被杀死,这些进程被保留在内存中以加快下次启动速度。 用户按了 Home 键后退到后台的 App
300 空进程 不包含任何活动或服务的进程,纯粹为了缓存。 被彻底从任务列表中划掉的 App
200 Content Provider 服务的进程。 某些 App 的 Content Provider
100 持久进程 通常指系统核心服务,如电话、系统设置等。 电话 App、系统设置
0 前台进程 当前正在与用户交互的进程,这是最高优先级的用户进程 用户正在使用的 App
较大值 后台空进程 空闲的后台进程,随时可被回收。 完全在后台且无服务的 App

注意:不同 Android 版本和厂商定制 ROM 中,这些 adj 值可能会有细微差异,但核心逻辑和等级划分基本一致。

low memory killer参数
(图片来源网络,侵删)

minfreeadj 的对应关系 (示例)

假设我们有一组典型的参数配置:

# cat /sys/module/lowmemorykiller/parameters/minfree
18432,23040,27648,34816,46080,86016
# cat /sys/module/lowmemorykiller/parameters/adj
0,200,400,900,1000,1200

这组参数可以这样解读:

  1. 当可用内存 <= 86MB (86016 KB)

    • 系统会开始杀死 adj>= 1200 的进程,这些通常是空进程,可以被安全地杀死而不会影响用户体验。
  2. 当可用内存 <= 45MB (46080 KB)

    low memory killer参数
    (图片来源网络,侵删)
    • 系统会开始杀死 adj>= 1000 的进程,这包括 adj=1200 的进程,如果还存在的话。
  3. 当可用内存 <= 34MB (34816 KB)

    • 系统会开始杀死 adj>= 900 的进程,这通常包括缓存进程 (如用户按了 Home 键的 App)。
  4. 当可用内存 <= 27MB (27648 KB)

    • 系统会开始杀死 adj>= 400 的进程,这可能会影响到一些次要服务进程
  5. 当可用内存 <= 22.5MB (23040 KB)

    • 系统会开始杀死 adj>= 200 的进程,这可能会影响到可见的进程Content Provider,系统会非常谨慎地处理。
  6. 当可用内存 <= 18MB (18432 KB)

    • 系统会开始杀死 adj>= 0 的进程,这包括前台进程!这是最严重的情况,系统为了不崩溃,可能会杀死用户正在使用的 App,导致 App 被强制关闭。

如何查看和修改这些参数?

查看当前参数

# 使用 cat 命令查看
cat /sys/module/lowmemorykiller/parameters/minfree
cat /sys/module/lowmemorykiller/parameters/adj
# 使用 dumpsys 命令查看更详细的内存信息
dumpsys meminfo

重要提示:在大多数设备上,这些文件是只读的,普通应用甚至 Root 后的普通用户也无法直接修改,修改这些参数通常需要重新编译内核或使用特定的系统级工具(如一些厂商的开发者选项或 Magisk 模块)。

修改参数的风险

  • 修改 minfree 值过高:将所有 minfree 值都设置得很大,这会导致系统在内存很低时才触发 LMK,后台会堆积大量进程,最终可能导致应用切换卡顿,甚至系统整体响应缓慢。
  • 修改 adj 值不合理:降低某个重要进程类型的 adj 值,可能会让它在不该被杀死的时候被杀死,导致系统功能异常。

对于普通用户和开发者来说,了解 LMK 的工作原理比去修改它更重要,系统厂商已经根据设备硬件和 ROM 特性对 LMK 参数进行了调优。


LMK 的演进:LMKd

在较新的 Android 版本中(尤其是 Android 9+),LMK 的用户态部分被一个名为 lmkd (Low Memory Daemon) 的守护进程所取代。

  • LMK (内核态):仍然保留在内核中,负责最终执行杀死进程的操作。
  • lmkd (用户态):负责监听内存压力信号,并根据更复杂的策略(如进程的内存占用、CPU 使用情况等)来决定哪些进程应该被杀死,然后通过 ioctl 系统调用通知内核 LMK。

这种设计将决策逻辑从内核移到了用户空间,使得策略更新和调试更加灵活和安全,并且减少了内核态的复杂性。

参数 作用 示例值 核心逻辑
minfree 内存阈值列表 18432,23040,... 当可用内存 <= �
-- 展开阅读全文 --
头像
2008款MacBook Air参数如何?性能还够用吗?
« 上一篇 11-30
amd vega frontier参数
下一篇 » 11-30

相关文章

取消
微信二维码
支付宝二维码

最近发表

标签列表

目录[+]