فرآیند اندروید قاتل کم حافظه ( lmkd
) وضعیت حافظه یک سیستم اندرویدی در حال اجرا را کنترل میکند و به فشار بالای حافظه با از بین بردن کمترین فرآیندهای ضروری واکنش نشان میدهد تا عملکرد سیستم را در سطوح قابل قبول حفظ کند.
درباره فشار حافظه
یک سیستم اندرویدی که چندین فرآیند را به صورت موازی اجرا میکند ممکن است با موقعیتهایی مواجه شود که حافظه سیستم تمام شده است و فرآیندهایی که به حافظه بیشتری نیاز دارند، تاخیرهای قابل توجهی را تجربه میکنند. فشار حافظه ، حالتی که در آن سیستم با حافظه کم کار می کند، به اندروید نیاز دارد که حافظه را آزاد کند (برای کاهش فشار) با خنثی کردن یا از بین بردن فرآیندهای غیر مهم، درخواست فرآیندهایی برای آزاد کردن منابع ذخیره شده غیر بحرانی و غیره.
از لحاظ تاریخی، اندروید فشار حافظه سیستم را با استفاده از درایور کشنده حافظه کم (LMK) درون هسته کنترل میکرد، مکانیزمی سفت و سخت که به مقادیر رمزگذاری شده بستگی دارد. از هسته 4.12، درایور LMK از هسته بالادست حذف می شود و فضای کاربر lmkd
نظارت بر حافظه و وظایف کشتن فرآیند را انجام می دهد.
اطلاعات ایستگاه فشار
اندروید 10 و نسخه های جدیدتر از حالت جدید lmkd
پشتیبانی می کند که از مانیتورهای اطلاعات توقف فشار هسته (PSI) برای تشخیص فشار حافظه استفاده می کند. پچست PSI در هسته بالادست (که به هستههای 4.9 و 4.14 پشتیبانگیری میشود) مدت زمانی را که وظایف به تاخیر میافتند در نتیجه کمبود حافظه اندازهگیری میکند. از آنجایی که این تأخیرها مستقیماً بر تجربه کاربر تأثیر می گذارد، معیاری مناسب برای تعیین شدت فشار حافظه است. هسته بالادستی همچنین شامل مانیتورهای PSI است که به فرآیندهای فضای کاربران ممتاز (مانند lmkd
) اجازه میدهد تا آستانههایی را برای این تأخیرها مشخص کنند و در صورت نقض آستانه، در رویدادهایی از هسته مشترک شوند.
مانیتورهای PSI در مقابل سیگنال های vmpressure
از آنجایی که سیگنالهای vmpressure
(که توسط هسته برای تشخیص فشار حافظه تولید میشوند و توسط lmkd
استفاده میشوند) اغلب شامل موارد مثبت کاذب متعددی میشوند، lmkd
باید فیلتر را انجام دهد تا تعیین کند که آیا حافظه تحت فشار واقعی است یا خیر. این منجر به بیدار شدن غیر ضروری lmkd
و استفاده از منابع محاسباتی اضافی می شود. استفاده از مانیتورهای PSI منجر به تشخیص دقیقتر فشار حافظه میشود و سربار فیلتر را به حداقل میرساند.
استفاده از مانیتورهای PSI
برای استفاده از نمایشگرهای PSI به جای رویدادهای vmpressure
، ویژگی ro.lmk.use_psi
را پیکربندی کنید. پیشفرض true
است، و باعث میشود PSI مکانیسم پیشفرض تشخیص فشار حافظه برای lmkd
را مانیتور کند. از آنجایی که مانیتورهای PSI به پشتیبانی هسته نیاز دارند، هسته باید شامل وصلههای پشتیبان PSI باشد و با پشتیبانی PSI فعال شده ( CONFIG_PSI=y
) کامپایل شود.
معایب درایور LMK درون هسته
Android درایور LMK را به دلیل تعدادی از مشکلات منسوخ می کند، از جمله:
- دستگاههای با رم پایین باید به شدت تنظیم میشدند، و حتی در آن زمان در بارهای کاری با کش صفحه فعال با پشتوانه فایلهای بزرگ عملکرد ضعیفی داشتند. عملکرد ضعیف منجر به ضربه زدن و بدون کشتن شد.
- درایور هسته LMK به محدودیتهای حافظه آزاد متکی بود، بدون اینکه مقیاسی بر اساس فشار حافظه ایجاد شود.
- به دلیل استحکام طراحی، شرکا اغلب درایور را سفارشی میکردند تا روی دستگاههایشان کار کند.
- راننده LMK به API کوچککننده اسلب متصل شد، که برای عملیاتهای سنگین مانند جستجوی اهداف و کشتن آنها طراحی نشده بود، که روند
vmscan
را کند کرد.
فضای کاربری lmkd
lmkd
همان عملکرد درایور درون هسته را پیاده سازی می کند اما از مکانیسم های هسته موجود برای تشخیص و تخمین فشار حافظه استفاده می کند. چنین مکانیزمهایی شامل استفاده از رویدادهای vmpressure
تولید شده توسط هسته یا نمایشگرهای اطلاعات توقف فشار (PSI) برای دریافت اعلانهای مربوط به سطوح فشار حافظه، و استفاده از ویژگیهای cgroup حافظه برای محدود کردن منابع حافظه اختصاص داده شده به هر فرآیند بر اساس اهمیت فرآیند است.
استفاده از userspace lmkd در اندروید 10
در اندروید 9 و جدیدتر، اگر درایور LMK درون هسته شناسایی نشود، userspace lmkd
فعال می شود. از آنجایی که userspace lmkd
به پشتیبانی هسته برای cgroup های حافظه نیاز دارد، هسته باید با تنظیمات پیکربندی زیر کامپایل شود:
CONFIG_ANDROID_LOW_MEMORY_KILLER=n
CONFIG_MEMCG=y
CONFIG_MEMCG_SWAP=y
استراتژی های کشتن
lmkd
از استراتژیهای کشتن مبتنی بر رویدادهای vmpressure
یا نمایشگرهای PSI، شدت آنها و نکات دیگری مانند استفاده از مبادله پشتیبانی میکند. استراتژیهای کشتن بین دستگاههای با حافظه کم و عملکرد بالا متفاوت است:
- در دستگاه های با حافظه کم، سیستم باید فشار حافظه بالاتری را به عنوان یک حالت عملکرد عادی تحمل کند.
- در دستگاه های با کارایی بالا، فشار حافظه باید به عنوان یک وضعیت غیرعادی در نظر گرفته شود و قبل از اینکه بر عملکرد کلی تأثیر بگذارد، رفع شود.
شما می توانید استراتژی kill را با استفاده از ویژگی ro.config.low_ram
کنید. برای جزئیات، تنظیمات پایین رم را ببینید.
lmkd
همچنین از یک حالت قدیمی پشتیبانی میکند که در آن با استفاده از استراتژیهای مشابه درایور LMK درون هسته (یعنی آستانههای حافظه آزاد و کش فایلها) تصمیمات مرگ را میگیرد. برای فعال کردن حالت قدیمی، ویژگی ro.lmk.use_minfree_levels
را روی true
تنظیم کنید.
پیکربندی lmkd
lmkd
را برای یک دستگاه خاص با استفاده از ویژگی های زیر پیکربندی کنید.
ویژگی | استفاده کنید | پیش فرض |
---|---|---|
ro.config.low_ram | مشخص کنید که دستگاه دارای رم کم یا عملکرد بالا است. | false |
ro.lmk.use_psi | از نمایشگرهای PSI (به جای رویدادهای vmpressure ) استفاده کنید. | true |
ro.lmk.use_minfree_levels | از حافظه آزاد و آستانه های کش فایل برای تصمیم گیری در مورد کشتن فرآیند استفاده کنید (یعنی مطابقت با عملکرد درایور LMK درون هسته). | false |
ro.lmk.low | حداقل امتیاز oom_adj برای فرآیندهایی که واجد شرایط حذف در سطح vmpressure پایین هستند. | 1001 (معلول) |
ro.lmk.medium | حداقل امتیاز oom_adj برای فرآیندهای واجد شرایط برای از بین بردن در سطح vmpressure متوسط. | 800 (خدمات کش یا غیر ضروری) |
ro.lmk.critical | حداقل امتیاز oom_adj برای فرآیندهای واجد شرایط برای از بین بردن در سطح vmpressure بحرانی. | 0 (هر فرآیندی) |
ro.lmk.critical_upgrade | فعال کردن ارتقا به سطح بحرانی | false |
ro.lmk.upgrade_pressure | حداکثر mem_pressure که در آن سطح ارتقا می یابد زیرا سیستم در حال تعویض بیش از حد است. | 100 (معلول) |
ro.lmk.downgrade_pressure | حداقل mem_pressure که در آن یک رویداد vmpressure نادیده گرفته می شود زیرا حافظه آزاد کافی هنوز در دسترس است. | 100 (معلول) |
ro.lmk.kill_heaviest_task | سنگین ترین کار واجد شرایط (بهترین تصمیم) را در مقابل هر کار واجد شرایط (تصمیم سریع) بکشید. | true |
ro.lmk.kill_timeout_ms | مدت زمان بر حسب میلی ثانیه پس از کشتن زمانی که کشتن اضافی انجام نخواهد شد. | 0 (معلول) |
ro.lmk.debug | گزارش های اشکال زدایی lmkd فعال کنید. | false |
نمونه پیکربندی دستگاه:
PRODUCT_PROPERTY_OVERRIDES += \
ro.lmk.low=1001 \
ro.lmk.medium=800 \
ro.lmk.critical=0 \
ro.lmk.critical_upgrade=false \
ro.lmk.upgrade_pressure=100 \
ro.lmk.downgrade_pressure=100 \
ro.lmk.kill_heaviest_task=true
فضای کاربری lmkd در اندروید 11
اندروید 11 با معرفی یک استراتژی جدید کشتار، lmkd
را بهبود می بخشد. استراتژی کشتن از مکانیزم PSI برای تشخیص فشار حافظه که در lmkd
10 معرفی شده است استفاده می کند. این استراتژی کشتار جایگزین استراتژیهای قبلی میشود و میتواند هم در دستگاههای با کارایی بالا و هم با رم پایین (Android Go) استفاده شود.
نیازهای هسته
برای دستگاههای Android 11، lmkd
به ویژگیهای هسته زیر نیاز دارد:
- وصلههای PSI را اضافه کنید و PSI را فعال کنید (پسپورتهای موجود در هستههای رایج اندروید ۴.۹، ۴.۱۴ و ۴.۱۹).
- شامل وصلههای پشتیبانی PIDFD (پشتپورتهای موجود در هستههای رایج اندروید 4.9، 4.14 و 4.19).
- برای دستگاههای با رم کم، cgroupهای حافظه را نیز شامل کنید.
هسته باید با تنظیمات پیکربندی زیر کامپایل شود:
CONFIG_PSI=y
پیکربندی lmkd در اندروید 11
استراتژی کشتن حافظه در اندروید 11 از دکمه های تنظیم و پیش فرض های ذکر شده در زیر پشتیبانی می کند. این ویژگی ها هم بر روی دستگاه های با کارایی بالا و هم در دستگاه های با رم کم کار می کنند.
ویژگی | استفاده کنید | پیش فرض | |
---|---|---|---|
عملکرد بالا | رم کم | ||
ro.lmk.psi_partial_stall_ms | آستانه توقف جزئی PSI، در میلی ثانیه، برای راه اندازی اعلان حافظه کم. اگر دستگاه اعلانهای فشار حافظه را خیلی دیر دریافت کرد، این مقدار را کاهش دهید تا اعلانهای زودتر فعال شوند. اگر اعلانهای فشار حافظه غیرضروری فعال میشوند، این مقدار را افزایش دهید تا دستگاه کمتر به نویز حساس شود. | 70 | 200 |
ro.lmk.psi_complete_stall_ms | آستانه کامل PSI، در میلی ثانیه، برای راه اندازی اعلان های حافظه حیاتی. اگر دستگاه اعلانهای فشار بحرانی حافظه را خیلی دیر دریافت میکند، این مقدار را کاهش دهید تا اعلانهای قبلی فعال شود. اگر اعلانهای فشار بحرانی حافظه غیرضروری فعال میشوند، این مقدار را افزایش دهید تا دستگاه نسبت به نویز حساسیت کمتری داشته باشد. | 700 | |
ro.lmk.thrashing_limit | حداکثر مقدار خطاهای مجموعه کاری به عنوان درصدی از کل اندازه کش صفحه پشتیبانشده فایل. خطاهای مجموعه کاری بالاتر از این مقدار به این معنی است که سیستم در نظر گرفته می شود که کش صفحه خود را thrash می کند. اگر عملکرد دستگاه در حین فشار حافظه تحت تأثیر قرار میگیرد، مقدار را کاهش دهید تا کوبیدن را محدود کنید. اگر عملکرد دستگاه به دلایل کوبیدن غیر ضروری از بین رفت، مقدار را افزایش دهید تا امکان کوبیدن بیشتر فراهم شود. | 100 | 30 |
ro.lmk.thrashing_limit_decay | فروپاشی آستانه کوبنده به صورت درصدی از آستانه اولیه استفاده شده برای پایین آوردن آستانه زمانی که سیستم بازیابی نمی شود، حتی پس از کشتن بیان می شود. اگر کوبیدن مداوم باعث کشتن غیر ضروری می شود، مقدار را کاهش دهید. اگر پاسخ به کوبیدن مداوم پس از کشتن خیلی کند است، مقدار را افزایش دهید. | 10 | 50 |
ro.lmk.swap_util_max | حداکثر مقدار حافظه تعویض شده به عنوان درصدی از کل حافظه قابل تعویض. هنگامی که حافظه swapped بیش از این حد رشد می کند، به این معنی است که سیستم بیشتر حافظه قابل تعویض خود را تعویض کرده و همچنان تحت فشار است. این ممکن است زمانی اتفاق بیفتد که تخصیصهای غیرقابل تعویض فشار حافظه ایجاد میکنند که با تعویض نمیتوان آن را کاهش داد زیرا بیشتر حافظه قابل تعویض قبلاً تعویض شده است. مقدار پیش فرض 100 است که عملاً این بررسی را غیرفعال می کند. اگر عملکرد دستگاه در حین فشار حافظه تحت تأثیر قرار می گیرد، در حالی که استفاده از مبادله زیاد است و سطح مبادله رایگان به ro.lmk.swap_free_low_percentage کاهش نمی یابد، مقدار را کاهش دهید تا استفاده از مبادله محدود شود. | 100 | 100 |
دستگیره های تنظیم قدیمی زیر نیز با استراتژی جدید کشتار کار می کنند.
ویژگی | استفاده کنید | پیش فرض | |
---|---|---|---|
عملکرد بالا | رم کم | ||
ro.lmk.swap_free_low_percentage | سطح مبادله رایگان به عنوان درصدی از کل فضای مبادله. «lmkd» از این مقدار بهعنوان آستانهای برای زمان در نظر گرفتن سیستم به عنوان فضای مبادله گرسنگی استفاده میکند. اگر «lmkd» در حالی که فضای زیادی در مبادله وجود دارد می کشد، درصد را کاهش دهید. اگر کشتنهای «lmkd» خیلی دیر اتفاق میافتند، با اجازه دادن به کشتنهای OOM، درصد را افزایش دهید. | 20 | 10 |
ro.lmk.debug | این گزارش اشکال زدایی lmkd را فعال می کند. هنگام تنظیم، اشکال زدایی را فعال کنید. | false |