خطای Out of Memory یکی از مشکلاتی است که ممکن است هنگام اجرای برنامهها و سرویسهای مختلف در سیستمعامل لینوکس با آن مواجه شوید. این خطا زمانی اتفاق میافتد که سیستم نتواند حافظه موردنیاز یک پردازش را تأمین کند. در چنین شرایطی ممکن است برنامهها بهدرستی اجرا نشوند، سرویسها متوقف شوند یا حتی برخی از پردازشهای سیستم بهصورت ناگهانی بسته شوند. شناخت دلایل بروز این مشکل و روشهای برطرف کردن آن برای افرادی که با سرورهای لینوکسی کار میکنند اهمیت زیادی دارد. برای مثال، اگر روی سرور مجازی ایران یا سرور مجازی خارج چندین سرویس و برنامه را بهصورت همزمان اجرا میکنید، مدیریت صحیح حافظه میتواند از بروز اختلال در عملکرد آنها جلوگیری کند. در این مقاله بررسی میکنیم که خطای Out of Memory چیست، چه ارتباطی با OOM Killer دارد و چگونه میتوان با استفاده از دستورات لینوکس، علت بروز آن را شناسایی و برطرف کرد.


خطای Out of Memory در لینوکس چیست؟
خطای Out of Memory که به اختصار OOM نیز نامیده میشود، زمانی رخ میدهد که سیستمعامل نتواند حافظه موردنیاز یک برنامه یا پردازش را تأمین کند. در لینوکس، حافظه اصلی سیستم (RAM) برای اجرای برنامهها، نگهداری دادههای موقت و مدیریت پردازشهای مختلف استفاده میشود.
هر برنامه هنگام اجرا به مقداری حافظه نیاز دارد. اگر مجموع حافظه موردنیاز پردازشها از منابع قابلاستفاده سیستم بیشتر شود، لینوکس تلاش میکند با روشهای مختلف فضای حافظه آزاد کند. در صورتی که این تلاشها کافی نباشند، ممکن است مکانیزم OOM Killer فعال شود تا با متوقف کردن برخی پردازشها، حافظه موردنیاز سایر بخشهای سیستم را تأمین کند.
برای مثال، فرض کنید یک سرور ۴ گیگابایت حافظه RAM دارد و چندین سرویس مانند وبسرور، پایگاه داده و برنامههای کاربردی روی آن اجرا میشوند. اگر یکی از برنامهها بهصورت غیرعادی حافظه زیادی مصرف کند، ممکن است منابع کافی برای اجرای سایر پردازشها باقی نماند. در این وضعیت احتمال بروز خطای Out of Memory افزایش پیدا میکند.
نکته مهم این است که این خطا همیشه به معنی خراب بودن حافظه RAM نیست؛ بلکه معمولاً نشاندهنده کافی نبودن منابع حافظه در دسترس یا وجود محدودیت در تخصیص حافظه است.
OOM Killer چیست و چگونه کار میکند؟
OOM Killer یکی از مکانیزمهای مدیریت حافظه در هسته لینوکس (Linux Kernel) است که وظیفه دارد هنگام کمبود شدید حافظه، برخی پردازشها را متوقف کند تا سیستم بتواند به فعالیت خود ادامه دهد.
زمانی که حافظه قابلاستفاده سیستم به اندازه کافی نباشد و راهکارهای معمول مدیریت حافظه نتوانند فضای موردنیاز را فراهم کنند، OOM Killer وارد عمل میشود. این مکانیزم پردازشهای در حال اجرا را بررسی میکند و بر اساس معیارهای مشخص، پردازشی را برای متوقف شدن انتخاب میکند.
انتخاب پردازش صرفاً بر اساس میزان RAM مصرفی آن انجام نمیشود. معیارهایی مانند مقدار حافظه مصرفشده، تنظیمات اولویت OOM و شرایط سیستم نیز در این تصمیم نقش دارند.
برای مثال، ممکن است یک پردازش پایگاه داده یا برنامه PHP به دلیل مصرف بالای حافظه توسط OOM Killer متوقف شود. در این شرایط، سرویس مربوطه ممکن است از دسترس خارج شود یا نیاز به راهاندازی مجدد داشته باشد.
توجه: فعال شدن OOM Killer لزوماً به معنی متوقف شدن کل سیستم نیست. این مکانیزم معمولاً تلاش میکند با پایان دادن به یک یا چند پردازش، از اختلال گستردهتر جلوگیری کند؛ بااینحال، اگر پردازش مهمی انتخاب شود، ممکن است عملکرد سرویسهای وابسته نیز تحت تأثیر قرار بگیرد.
دلایل بروز خطای Out of Memory در لینوکس
این خطا میتواند به دلایل مختلفی اتفاق بیفتد. برای رفع اصولی آن، ابتدا باید مشخص کنید چه عاملی باعث افزایش مصرف حافظه یا محدود شدن منابع قابلاستفاده شده است.
پر شدن حافظه RAM
یکی از رایجترین دلایل بروز خطای Out of Memory، پر شدن حافظه RAM است. هر پردازش در حال اجرا بخشی از حافظه سیستم را در اختیار میگیرد و با افزایش تعداد برنامهها، میزان مصرف RAM نیز بیشتر میشود.
اگر ظرفیت حافظه برای پاسخگویی به نیاز تمام پردازشها کافی نباشد، سیستم ممکن است با کمبود حافظه مواجه شود.
این مشکل معمولاً در سرورهایی دیده میشود که چندین سرویس مانند MySQL، Apache، Nginx و برنامههای مختلف بهصورت همزمان روی آنها اجرا میشوند.
مصرف بیش از حد حافظه توسط یک پردازش
گاهی اوقات مشکل از ظرفیت کلی RAM نیست، بلکه یک برنامه بهصورت غیرعادی حافظه زیادی مصرف میکند.
برای مثال، وجود Memory Leak در یک برنامه میتواند باعث شود حافظهای که دیگر موردنیاز نیست، بهدرستی آزاد نشود. در نتیجه با گذشت زمان، میزان مصرف RAM افزایش پیدا میکند و احتمال بروز خطای Out of Memory بیشتر میشود.
اجرای پردازشهای سنگین، تنظیمات نامناسب برنامهها و مدیریت نادرست حافظه نیز میتوانند چنین شرایطی ایجاد کنند.
تنظیم نبودن فضای Swap
Swap فضایی از حافظه ذخیرهسازی است که لینوکس میتواند در شرایط خاص برای نگهداری بخشی از صفحات حافظه استفاده کند.
زمانی که RAM تحت فشار قرار میگیرد، سیستمعامل ممکن است برخی از صفحات حافظه را به فضای Swap منتقل کند تا بخشی از RAM آزاد شود.
اگر فضای Swap وجود نداشته باشد یا ظرفیت آن برای شرایط کاری سیستم کافی نباشد، احتمال بروز مشکل کمبود حافظه افزایش پیدا میکند.
البته باید توجه داشت که Swap جایگزین کامل RAM نیست؛ زیرا سرعت خواندن و نوشتن اطلاعات روی دیسک معمولاً بسیار کمتر از سرعت دسترسی به حافظه اصلی است.
محدودیت حافظه در کانتینرها
در محیطهایی مانند Docker و Kubernetes ممکن است برای هر کانتینر محدودیت مشخصی در مصرف حافظه تعریف شده باشد.
در این شرایط، حتی اگر سیستم میزبان (Host) حافظه آزاد داشته باشد، عبور یک کانتینر از محدودیت تعیینشده میتواند باعث توقف پردازشهای آن شود.
بنابراین همیشه لازم نیست خطای Out of Memory به دلیل پر شدن تمام RAM سرور اتفاق بیفتد. گاهی محدودیت حافظه یک سرویس یا کانتینر عامل اصلی بروز مشکل است.
چگونه خطای Out of Memory در لینوکس را شناسایی کنیم؟
برای شناسایی علت خطای Out of Memory بهتر است ابتدا وضعیت حافظه و پردازشهای فعال را بررسی کنید. لینوکس ابزارهای مختلفی برای مشاهده میزان مصرف RAM و بررسی گزارشهای سیستم در اختیار کاربران قرار میدهد.
بررسی میزان حافظه با دستور free
یکی از سادهترین روشها برای بررسی وضعیت حافظه در لینوکس، استفاده از دستور free است.
برای مشاهده اطلاعات حافظه، دستور زیر را در ترمینال اجرا کنید:
free -h
گزینه h- باعث میشود مقادیر حافظه با واحدهای خواناتر مانند MB و GB نمایش داده شوند.
خروجی این دستور شامل اطلاعاتی مانند موارد زیر است:
- Totalمجموع حافظه RAM سیستم
- Usedمقدار حافظه استفادهشده
- Freeمقدار حافظه کاملاً آزاد
- Sharedحافظه مشترک بین پردازشها
- Buff/Cacheحافظه استفادهشده برای بافر و کش
- Availableتخمینی از حافظهای که بدون ایجاد فشار جدی بر سیستم میتواند در اختیار برنامهها قرار بگیرد.
در این خروجی، مقدار Available اهمیت زیادی دارد؛ زیرا مقدار Free بهتنهایی معیار مناسبی برای تشخیص کمبود حافظه نیست. لینوکس از RAM آزاد برای کش و بافر استفاده میکند و در صورت نیاز میتواند بخشی از آن را آزاد کند.
بررسی پردازشهای پرمصرف با دستور top
برای شناسایی برنامههایی که بیشترین میزان حافظه را مصرف میکنند، میتوانید از دستور top استفاده کنید.
top
پس از اجرای دستور، فهرستی از پردازشهای فعال و اطلاعات مربوط به آنها نمایش داده میشود.
ستونهای مهم در این خروجی عبارتاند از:
- PIDشناسه پردازش
- USERکاربری که پردازش را اجرا کرده است.
- MEM%درصد حافظه RAM مصرفشده توسط پردازش
- RESمقدار حافظه فیزیکی مورد استفاده پردازش
- COMMANDنام دستور یا برنامه اجراشده
برای مرتبسازی پردازشها بر اساس میزان مصرف حافظه، میتوانید پس از اجرای top کلید Shift + M را فشار دهید.
به این ترتیب، پردازشهایی که بیشترین میزان حافظه را مصرف میکنند در بالای فهرست قرار میگیرند.
مشاهده گزارشهای OOM در لاگهای سیستم
یکی از دقیقترین روشها برای بررسی علت بروز خطای Out of Memory، مشاهده گزارشهای ثبتشده توسط هسته لینوکس است.
برای مشاهده پیامهای مرتبط با OOM میتوانید از دستور زیر استفاده کنید:
sudo dmesg -T | grep -i -E 'out of memory|oom|killed process'
این دستور پیامهای مرتبط با کمبود حافظه و پردازشهایی را که توسط OOM Killer متوقف شدهاند، نمایش میدهد.
همچنین در سیستمهایی که از systemd استفاده میکنند، میتوانید گزارشهای هسته را با دستور زیر بررسی کنید:
sudo journalctl -k | grep -i -E 'out of memory|oom|killed process'
در خروجی این دستورات ممکن است اطلاعاتی مانند نام پردازش متوقفشده، شناسه آن و دلیل فعال شدن OOM Killer را مشاهده کنید.
برای مثال، اگر نام یک پردازش PHP یا MySQL در گزارشها دیده شود، میتوانید بررسی را روی تنظیمات و میزان مصرف حافظه همان سرویس متمرکز کنید.
روشهای رفع خطای Out of Memory در لینوکس
پس از شناسایی علت بروز مشکل، میتوانید متناسب با شرایط سیستم از روشهای مختلفی برای رفع خطای Out of Memory استفاده کنید.
شناسایی و مدیریت پردازشهای پرمصرف
اگر یک پردازش بخش زیادی از حافظه سیستم را مصرف میکند، ابتدا باید دلیل این مصرف بالا را مشخص کنید.
برای این کار میتوانید از دستور top یا htop استفاده کنید و پردازشهای پرمصرف را شناسایی کنید.
در صورتی که مطمئن شدید یک پردازش غیرضروری است و متوقف کردن آن مشکلی برای سیستم ایجاد نمیکند، میتوانید با استفاده از PID آن را متوقف کنید.
kill PID
بهجای PID باید شناسه واقعی پردازش را قرار دهید.
این دستور ابتدا درخواست خاتمه عادی پردازش را ارسال میکند. اگر پردازش به این درخواست پاسخ ندهد، میتوان در شرایط ضروری از دستور زیر استفاده کرد:
kill -9 PID
هشدار: استفاده از kill -9 باعث خاتمه اجباری پردازش میشود و ممکن است اطلاعات ذخیرهنشده یا عملیات در حال اجرا از بین بروند. همچنین توقف پردازشهای مهم مانند پایگاه داده یا سرویسهای اصلی سیستم بدون بررسی وابستگیها توصیه نمیشود.
افزایش فضای Swap
اگر سیستم فضای Swap ندارد یا ظرفیت آن متناسب با شرایط کاری نیست، میتوانید با ایجاد یک فایل Swap بخشی از فشار حافظه را مدیریت کنید.
در ادامه مراحل ایجاد یک فایل Swap با ظرفیت ۲ گیگابایت را بررسی میکنیم.
مرحله اول: بررسی وضعیت فعلی Swap
ابتدا دستور زیر را اجرا کنید:
swapon --show
اگر خروجی خالی باشد، یعنی در حال حاضر فضای Swap فعالی در سیستم وجود ندارد.
مرحله دوم: ایجاد فایل Swap
برای ایجاد فایل Swap با ظرفیت ۲ گیگابایت از دستور زیر استفاده کنید:
sudo fallocate -l 2G /swapfile
این دستور یک فایل با حجم ۲ گیگابایت در مسیر مشخصشده ایجاد میکند.
مرحله سوم: تنظیم مجوزهای فایل
برای جلوگیری از دسترسی کاربران غیرمجاز به فایل Swap، مجوزهای آن را محدود کنید:
sudo chmod 600 /swapfile
مرحله چهارم: آمادهسازی فایل Swap
اکنون باید فایل ایجادشده را به فضای Swap تبدیل کنید:
sudo mkswap /swapfile
مرحله پنجم: فعال کردن Swap
برای فعالسازی فضای Swap دستور زیر را اجرا کنید:
sudo swapon /swapfile
مرحله ششم: بررسی فعال شدن Swap
در پایان با اجرای دستور زیر میتوانید وضعیت فضای Swap را بررسی کنید:
free -h
اگر مراحل بهدرستی انجام شده باشند، ظرفیت Swap در خروجی نمایش داده میشود.
برای فعال ماندن این تنظیم پس از راهاندازی مجدد سرور، باید مسیر فایل را به فایل /etc/fstab اضافه کنید:
/swapfile none swap sw 0 0
نکته: پیش از ویرایش فایل /etc/fstab از تنظیمات فعلی نسخه پشتیبان تهیه کنید و مطمئن شوید فایل Swap بهدرستی ایجاد شده است. همچنین در برخی فایلسیستمها، از جمله بعضی تنظیمات Btrfs، روش ایجاد فایل Swap متفاوت است و باید از روش سازگار با فایلسیستم استفاده کنید.
افزایش حافظه RAM
اگر مصرف حافظه سیستم بهصورت مداوم بالا است و برنامهها واقعاً به منابع بیشتری نیاز دارند، افزایش RAM میتواند راهکار مناسبی باشد.
این موضوع بهخصوص در سرورهایی اهمیت دارد که چندین سرویس سنگین را بهصورت همزمان اجرا میکنند.
برای مثال، اگر یک سرور علاوه بر وبسرور، پایگاه داده و چند برنامه کاربردی را نیز اجرا میکند، ممکن است ظرفیت فعلی RAM پاسخگوی نیاز آن نباشد.
در چنین شرایطی میتوانید با ارتقای منابع سختافزاری، ظرفیت حافظه بیشتری در اختیار سیستم قرار دهید.
البته پیش از افزایش RAM بهتر است میزان مصرف واقعی برنامهها و امکان بهینهسازی آنها را نیز بررسی کنید؛ زیرا گاهی مشکل از تنظیمات نادرست یک سرویس است، نه کمبود منابع سختافزاری.
بررسی محدودیت حافظه سرویسها و کانتینرها
اگر از Docker یا سایر ابزارهای مدیریت کانتینر استفاده میکنید، باید محدودیت حافظه تعریفشده برای هر کانتینر را بررسی کنید.
برای مثال، در Docker میتوانید با دستور زیر وضعیت مصرف منابع کانتینرهای فعال را مشاهده کنید:
docker stats
این دستور اطلاعاتی مانند مصرف CPU، حافظه و میزان استفاده از شبکه را نمایش میدهد.
اگر مشخص شد یک کانتینر به محدودیت حافظه خود رسیده است، باید تنظیمات منابع آن را بررسی کنید.
در چنین شرایطی میتوانید با توجه به ظرفیت واقعی سرور، محدودیت حافظه کانتینر را افزایش دهید یا مصرف حافظه برنامه داخل آن را کاهش دهید.
توجه داشته باشید که افزایش محدودیت حافظه کانتینر بدون در نظر گرفتن RAM کل سیستم ممکن است فشار بیشتری به میزبان وارد کند.
بهینهسازی مصرف حافظه برنامهها
در برخی موارد، مشکل کمبود حافظه به نحوه عملکرد خود برنامه مربوط میشود.
برای مثال، برنامهای که حجم زیادی از اطلاعات را بهصورت همزمان در حافظه بارگذاری میکند، ممکن است منابع زیادی مصرف کند.
برای کاهش این مشکل میتوانید اقدامات زیر را انجام دهید:
- بررسی و رفع Memory Leak در کد برنامه
- کاهش تعداد پردازشهای همزمان
- بهینهسازی کوئریهای پایگاه داده
- تنظیم مناسب تعداد Workerهای وبسرور
- محدود کردن حجم دادههای بارگذاریشده در حافظه
- بررسی تنظیمات حافظه سرویسهایی مانند PHP و MySQL
بهینهسازی برنامهها میتواند فشار واردشده به RAM را کاهش دهد و از تکرار خطای Out of Memory جلوگیری کند.




























بدون دیدگاه