خطای ۵۰۳ چیست؟ چطور آن را رفع کنیم؟
  • مقالات
  • 1401/03/11

خطای ۵۰۳ چیست؟ چطور آن را رفع کنیم؟

ر این مقاله، چگونگی رفع خطای ۵۰۳ در وب‌ سرور را آموزش می‌دهیم. کدهایی که با عدد ۵ شروع می‌شوند، بیانگر ایرادی از جانب سرور هستند. این کد هم به ما می‌گوید که سرور به دلایلی، امکان پاسخگویی به درخواست شما را ندارد.

اگر دوست دارید با انواع این کدها بیشتر آشنا شوید، مقاله خطاهای HTTP را بخوانید.

رایج‌ترین دلیلی که باعث بروز خطای 503 می‌شود، Crash شدن PHP است. حالا جدا از دلایل منجر به این اتفاق، بیایید سراغ راه‌حل برویم.

اقدامات اولیه در راستای رفع خطای ۵۰۳!

قبل از هرکاری،طبق اعلام سایت رسمی مستندات لایت اسپید جهت تست، باید آن را (حداقل به‌صورت موقت)، به آپاچی تغییر دهید. دو حالت پیش می‌آید:

  • دیگر با خطای ۵۰۳ مواجه نمی‌شوید؛ این یعنی ایراد از لایت اسپید است و این وب‌سرور است که منجر به بروز خطا می‌شود.
  • همچنان با خطای ۵۰۳ دست‌وپنجه نرم می‌کنید؛ این یعنی ایراد از جای دیگری است. راهکارهایی که در ادامه آورده‌ایم، برای این مورد است؛ برای زمانی که حتی با انتقال به آپاچی هم مشکل رفع نشود!

خب اول یک راهنمای سریع برای عیب‌یابی خواهیم داشت:

راهنمای عیب‌یابی سریع

در نهایت، شاید نیاز به پشتیبانی حرفه‌ای داشته باشید؛ اما قبل از آن، بد نیست اقدامات زیر را انجام دهید. شاید خودتان توانستید به‌راحتی مشکل را برطرف کنید!


  • صفحه phpinfo کاربری که دچار مشکل شده است را چک کنید. اگر چنین صفحه‌ای وجود ندارد، یک فایل php ایجاد کنید.
  • معمولاً error_log یا log سرور، راهکارهایی برای رفع مشکل ارائه می‌کنند. مثلاً شاید ایراد از memory باشد و راهکار هم در این لاگ‌ها ارائه شده باشد.
  • قابلیت opcode cacheورژن PHP را غیرفعال کنید.برای راستی‌آزمایی می‌توانید از صفحه phpinfo استفاده کنید.
  • افزونه‌های نامطمئن (از نظر ایمنی) PHP را غیرفعال کنید. افزونه‌هایی مثل ZendGuardLoader, Suhosin, ionCube و ….
  • فضای موجود روی هاردتان یا همان Disk Space را بررسی کنید.
  • اگر از CloudLinux استفاده می‌کنید، محدودیت تعیین‌شده برای Live memory را بررسی کنید. شاید نیاز به افزایش داشته باشد!
  • اگر از CloudLinux استفاده می‌کنید، محدودیت تعیین‌شده برای Live processرا بررسی کنید. شاید نیاز به افزایش داشته باشد!
  • بالا بردن محدودیت تعیین‌شده برای PHP memory هم راهکار موثری است. برای تائید آن می‌توانید از php کمک بگیرید.

این‌ها اقدامات دم‌دستی‌ای بودند که ممکن است بتوانند مشکل‌تان را برطرف کنند؛ اما اگر موفق نشدید، اصلاً جای نگرانی نیست. با ما همراه باشید و سراغ Log Files بروید.

بررسی Log Files

لاگ فایل‌های زیادی هستند که برای رفع مشکل کردن ارور 503 کمک‌تان می‌کنند. در ادامه 4 مورد از این Log Files را با هم بررسی می‌کنیم. محل قرارگیری آن‌ها را یاد می‌گیریم و می‌فهمیم که چه اطلاعاتی را در اختیارمان می‌گذارند.

اگر قصد عیب‌یابی از طریق این فایل‌ها را دارید، بهتر است با همین ترتیبی که ما آن‌ها را معرفی می‌کنیم پیش بروید.

1- Standard error log (stderr.log)

فایل stderr.log، حاوی ارورهای رایجی است که هنگام اجرای PHP رخ می‌دهند. این فایل معمولاً در یکی از دو دایرکتوری /var/log/apache2/ یا /usr/local/lsws/logs/ پیدا می‌شود.

اتفاقاً بیشترین کاربرد این فایل، پیدا کردن دلیل ارور ۵۰۳ است!

برای مثال، نمونه زیر خروجی‌ای است که از این لاگ دریافت خواهید کرد:

[STDERR] fork() failed, please increase process limit: Cannot allocate memory

2- Web Server Error Log

در این مورد، Error Log توسط وب‌سرور ایجاد می‌شود. این فایل هم در یکی از سه دایرکتوری /var/log/apache2/ یا /usr/local/lsws/logs/ یا /var/log/httpd/error_log قرار دارد! Error Log وب‌سرور، علاوه‌بر اینکه مشخص می‌کند ایراد از وب‌سرور است یا نه، راهکارهای کارآمدی را هم در اختیارتان می‌گذارد.

مثال زیر، یک نمونه خروجی از ارور لاگ وب سرور است:

[INFO] [319934] [1.1.1.1:49873-1#APVH:lsapi] connection to [uds://tmp/lshttpd/APVH-php56.sock] on request #0, confirmed, 0, associated process: 0, running: 0, error: Too many open files!

اگر می‌خواهید تعداد خطاهای ۵۰۳ را متوجه شوید، یا می‌خواهید بفهمید از آخرین باری که مشکل را برطرف کرده‌اید، آیا مجدداً خطای ۵۰۳ رخ داده یا نه، باید از دستور زیر استفاده کنید:

grep oops /etc/apache2/logs/error_log

نکته: در بیشتر مواقع، دلیل بروز این خطا ارائه نمی‌شود. بلکه فقط زمان و دامنه‌ای که درگیر بوده نمایش داده می‌شود.

3- System Log

این لاگ خطا، توسط سیستم‌عامل ایجاد می‌شود. برای پیدا کردن آن هم باید در یکی از ۲ دایرکتوری /var/log/messages یا /var/log/syslog دنبالش بگردید. اگر PHP به هر نحوی تحت تاثیر سیستم‌عامل قرار گرفته باشد، استفاده از این لاگ کمک‌تان می‌کند.

مثال زیر:

lfd[18304]: *User Processing* PID:18264 Kill:1 User:xxxxx VM:538(MB) EXE:/usr/local/lsws/fcgi-bin/lsphp-5.4.42 CMD:lsphp5

خروجی بالا، نشان می‌دهد که پروسه lsphp توسط فایروال lfd از بین رفته است. در واقع باید lsphp را از lfd حذف کنید.

4- PHP Error Log

این لاگ در php.ini تعریف می‌شود. می‌توانید phpinfo.php را برای پیدا کردن php error_log جست‌و‌جو کنید. کنترل‌پنل سی‌پنل، به‌صورت پیش‌فرض آن را در error_log قرار می‌دهد. PHP وقتی خطا، هشدار یا هرچیز مشابه دیگری را شناسایی کند، بسته به سطح لاگی که به آن دسترسی دارید، چنین لاگی را می‌سازد.

معمولاً این لاگ، داخل همان فولدری که PHP اجرا می‌شود، ساخته می‌شود.

مثال زیر، یک خروجی از PHP Error Log را نشان می‌دهد:

Fatal error: Call to undefined function my_function() in /home/mysite/public_html/test.php on line 2

معمولاً 3 نوع خطا در اپلیکیشن PHP که در حال استفاده از آن هستید رخ می‌دهد. بهترین راه برای مقابله با آن‌ها، ارسال این لاگ‌ها برای توسعه‌دهنده اپلیکیشن مبتنی‌بر PHP است.

خب برویم سراغ عیب‌یابی دقیق‌تر!

عیب‌یابی

در این بخش، چگونگی عیب‌یابی خطای ۵۰۳ را به دو صورت مقدماتی و پیشرفته بررسی خواهیم کرد.

حتما بخوانید:  چگونگی حذف یک تصویر از نتایج گوگل

عیب‌یابی مقدماتی

خود این بخش، به قسمت‌های مختلف تقسیم می‌شود:

Display Errors

در محیط‌ عمل، رایج است که اپلیکیشن مبتنی‌بر PHP را از نمایش خطا منع می‌کنند! این کار برای حفاظت از سرور، هنگام بروز خطا انجام می‌شود. البته اگر بخواهید دلیل بروز خطای ۵۰۳ را تشخیص دهید، این کار به‌نوعی مانع عملیات می شود!

اگر خطای 503 برای یک سایت یا دامنه مشخص رخ داده است، کد زیر را درست بعد از <?php و در اسکریپت مشابه با خطای 503 وارد کنید:

<?php # The opening PHP tag
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);

حالا وقتی قصد بازدید از صفحه وب را داشته باشید، احتمالاً با خطایی مشابه خطای زیر مواجه خواهید شد:

Fatal error: Call to undefined function my_function() in /home/mysite/public_html/test.php on line 2

معمولاً این خطا، هیچ ارتباطی با وب‌سرور ندارد. در واقع، یک ایراد از جانب کد است! توصیه ما این است که Stack Overflow را بررسی کنید. همچنین می‌توانید با توسعه‌دهنده نرم‌افزار برای رفع مشکل تماس بگیرید.

نکته: بعد از اینکه خطا را شناسایی کردید، حتماً فایل را به مکان قبلی‌اش بازگردانید تا امنیت سرورتان حفظ شود.

PHP Info Page

این بخش (PHP info page)، اطلاعات بسیار زیادی را در رابطه با نصب PHP در اختیارمان می‌گذارد. این صفحه یک فایل کاملاً مقدماتی است که نباید خطای 503 را نشان‌مان دهد:

<?php
echo phpinfo();
?>

نکته: اگر در PHP info page با خطای 503 مواجه شدید، این بخش کمک‌تان نخواهد کرد!

صفحه PHP info

نکته: اگر در PHP info page با خطای 503 مواجه شدید، این بخش کمک‌تان نخواهد کرد!

از جمله اطلاعاتی که PHP info page ارائه می‌کند، موارد زیر هستند:

  • افزونه‌ها (Extensions)
  • محدودیت مموری (Memory Limit)
  • زمان اجرا (Execution Time)
  • تنظیمات دیگر (Other Settings)

تصویر بالا، یک صفحه PHP info page را نشان می‌‌دهد.

اگر به این تصویر دقت کنید، می‌بینید که OPCache فعال است، مقدار محدودیت مموری یا memory limit را خواهید دید، می‌توانید بفهمید کدام افزونه‌ها در حال کار هستند و …. تمام این اطلاعات، برای پیدا کردن دلیل خطای 503 بسیار مفید هستند.

همچنین این صفحه، می‌تواند برای مقایسه بین پیاده‌سازی‌های PHP دو وب‌سرور آپاچی و لایت اسپید هم کارآمد باشد.

Extensions

بسیاری از افزونه‌های مفید PHP هستند که منجر به بروز این خطا می‌شوند! مخصوصاً وقتی به‌روزرسانی نشده باشند!

مثل موارد زیر:

  • Imunify360
  • ZendGuardLoader
  • Suhosin
  • ionCube

توصیه اول اینکه دائماً این افزونه‌ها را به‌روزرسانی کنید؛ اما اگر از آخرین نسخه آن‌‌ها استفاده می‌کنید و همچنان مشکل برقرار است، غیرفعال‌شان کنید! اگر مشکل برطرف شد که دلیل آن هم مشخص می‌شود.

اما اگر مشکل همچنان برقرار بود، تمام افزونه‌هایی که به‌صورت پیش‌فرض فعال نبودند را غیرفعال کنید. حالا مجدداً بررسی کنید. اگر خطا برطرف شده بود که هیچ، اگر نه همراه‌مان باقی بمانید.

OPCache

این نوع کش، در واقع پروسه نگهداری از بایت کدها در حافظه اشتراکی است! به این ترتیب، دیگر نیازی است PHP یک پروسه مشابه را هربار بازخوانی کند؛ اما خب OPCache می‌تواند منجر به بروز مشکلاتی شود.

هنگامی که قصد پیدا کردن منشاء ایراد 503 را دارید، حتماً و حتماً OPcache را غیرفعال کنید.

موارد زیر، رایج‌ترین افزونه‌های OPCache هستند:

  • OPCache
  • APC/u
  • XCache
  • eAccelerator

دستور زیر، نمونه خطایی است که به OPCache ارتباط دارد:

[STDERR] zend_mm_heap corrupted

Disk Space

در برخی مواقع، PHP فایل‌ها را روی سرور ذخیره می‌کند تا بتواند عملکرد درستی داشته باشد. اگر حافظه‌تان تکمیل باشد، مخصوصاً قسمتی از آن که از /tmp/ نگهداری می‌کند، می‌تواند دلیلی برای خطای ۵۰۳ باشد.

برای بررسی میزان استفاده از هاردتان، می‌توانید دستور $ sudo df -h را اجرا کنید.

مثال زیر، یک نمونه از خروجی این دستور است:

$ sudo df -h
Filesystem                          Size  Used Avail Use% Mounted on
devtmpfs                            901M     0  901M   0% /dev
tmpfs                               915M   96K  915M   1% /dev/shm
tmpfs                               915M   89M  827M  10% /run
tmpfs                               915M     0  915M   0% /sys/fs/cgroup
/dev/mapper/cl_centos                29G  4.2G   25G  15% /
/dev/vda1                           976M  184M  726M  21% /boot
tmpfs                               183M     0  183M   0% /run/user/0

اگر حافظه‌تان پُر است، فایل‌های قدیمی را پاک کنید. ممکن است انجام این کار، مشکل خطای ۵۰۳ را حل کند.

Memory Limit

وقتی PHP به محدودیت حافظه‌ای که برایش تعیین شده می‌رسد، اصطلاحاً Crash می‌کند. 2 نوع مختلف از memory limit وجود دارد که PHP باید به آن‌ها پایبند باشد:

  1. memory limit داخلی که با ini تنظیم می‌شود.
  2. memory limit مربوط به LiteSpeedکه داخل وب‌سرور تنظیم می‌شود. این کار برای زمانی است که پروسه‌های PHP در حال زادوولد و زیاد شدن هستند.

دو نمونه زیر، برای مواقعی هستند که خطا مرتبط با ایرادات مموری است:

Fatal error: Allowed memory size of 33554432 bytes exhausted (tried to allocate 12864 bytes)
[STDERR] fork() failed, please increase process limit: Cannot allocate memory

اگر موافق باشید، هر دو نوع محدودیت در مموری را کمی دقیق‌تر بررسی کنیم.

PHP MEMORY

اگر خطایی که دریافت می‌کنید مثل یکی از موارد بالا است، اولین قدم در عیب‌یابی، افزایش میزان محدودیت در مموری یا همان Memory limit است. می‌توانید تنظیماتی که در ادامه آورده‌ایم را در php.ini اعمال کنید:

memory_limit = 100M

برای اینکه بفهمید مکان قرارگیری فایل php.ini و memory limit کنونی، می‌توانید یک صفحه PHP info بسازید. دستور زیر کمک‌تان می‌کند:

<?php
echo phpinfo();
?>

در برخی مواقع، ممکن است خطوط مختلف اسکریپت به .htaccess ضمیمه شوند. این کار به‌منظور بازنویسی تنظیمات PHP انجام می‌شود. همچنین این کار باعث بازنویسی تمام تنظیمات درون فایل php.ini می‌شود.

مثال زیر، یک نمونه از ورودی memory limit در .htaccess را نشان می‌دهد:

php_value memory_limit xxxM


برای اضافه کردن، پاک کردن یا حتی اعمال تنظیمات روی این خط کد، باید وارد .htaccess شوید.

CLOUDLINUX MEMORY LIMIT

اگر از CLoudLinx و Lightweight Virtual Environment یا به اختصار LVE، استفاده می‌کنید، ممکن است به محدودیت تعیین‌شده توسط اکانت رسیده باشید.

تصویر بالا نشان می‌دهد که اکانت‌ها به محدودیت رسیده‌اند. بسته به محدودیتی که اکانت با آن مواجه شده است، باید آن را تنظیم کنید.

LITESPEED PHP PROCESS MEMORY

اگر محدودیت تعیین‌شده برای مموری را در php.ini افزایش داده‌اید و تائید شده که به LVE limit نرسیده‌اید، شاید لازم باشد LSPHP  حافظه مجازی‌اش را افزایش دهد.

حتما بخوانید:  آموزش نصب zabbix 2.0.x

با انجام اقدامات زیر، می‌توانید این کار را انجام دهید:

  1. به کنسول مدیریت ادمین‌تان (https://YOUR_SERVER_IP:7080) بروید و لاگین کنید.
  2. سپس به <Configuration Server > PHP بروید.
  3. حالا برای تغییر تنظیمات مدنظر، روی Edit کلیک کنید.
  4. تنظیمات زیر را اعمال کنید و پس از آن روی Save کلیک کنید.
  • Memory Soft Limit: 4097M
  • Memory Hard Limit: 4098M
  1. حالا که همه‌چیز تنظیم شده است، به قسمت Actions بروید و روی آیکون Restart Detached PHP Processes کلیک کنید. در مرحله آخر هم Apply Changes < Graceful Restart.

Max Execution Time

اگر نهایت حد Execution Time به‌ اندازه‌ای نباشد که بتواند درخواست‌ها طولانی را مدیریت کند، ممکن است با این خطا که مربوط به لاگ وب‌سرور است مواجه شوید: error: Connection reset by peer

همچنین داشتن مقدار ، این معنی را می‌رساند که فرایند هیچ‌وقت درخواست را به اتمام نمی‌رساند. چنین خطاهایی معمولاً در stderr.log نشان داده می‌شوند. اگر این لاگ هم اطلاعات مفیدی ارائه نکرد، می‌توانید میزان max execution time را افزایش دهید.

Max Execution Time

اگر نهایت حد Execution Time به‌ اندازه‌ای نباشد که بتواند درخواست‌ها طولانی را مدیریت کند، ممکن است با این خطا که مربوط به لاگ وب‌سرور است مواجه شوید: error: Connection reset by peer

همچنین داشتن مقدار ، این معنی را می‌رساند که فرایند هیچ‌وقت درخواست را به اتمام نمی‌رساند. چنین خطاهایی معمولاً در stderr.log نشان داده می‌شوند. اگر این لاگ هم اطلاعات مفیدی ارائه نکرد، می‌توانید میزان max execution time را افزایش دهید.

PHP suEXEC Max Conn

ممکن است در لاگ stderr.log، چیزی مشابه پیام زیر ببینید:

[30117] Reached max children process limit: 10, extra: 3, current: 13, busy: 13, please increase LSAPI_CHILDREN.

PHP SuXEC Max Conn روی 10 تنظیم شده است، اما دامنه به 13 فرایند PHP نیاز دارد. برای افزایش LSAPI_CHILDREN، به LSWS WebAdmin > Server > General > PHP suEXEC Max Conn بروید و مقدار آن را افزایش دهید. مثلاً در این مورد، عدد 20 را درنظر بگیرید. LSWS و pkill lsphp را Restart کنید تا تنظیمات جدید اعمال شوند.

اگر خطا همچنان وجود داشت، می‌توانید به افزایش مقدار PHP suEXEC Max Conn، تا زمانی که خطا از بین برود ادامه دهید.

CSF/LFD

اگر CSF/LFD را نصب دارید، ممکن است همین‌ها منجر به خطای 503 شوند. این برنامه‌ها می‌توانند فرایند را قبل از به اتمام رسیدن نابود کنند.

CSF/LFD دو نوع تنظیمات دارد که می‌تواند قاتل جان یک فرایند LSPHP باشد:

PT_USERTIME و PT_FORKBOMB

KILL

ممکن است دلیل طولانی شدن تکمیل فرایند LSPHP، فراخوانی PT_USERTIME برای نابودی آن باشد. اگر عملیات نابودسازی موفق باشد، احتمالاً یک ایمیل یا پیامی در /var/log/lfd.log دریافت خواهید کرد که حاوی پیغام زیر است:

lfd[18304]: *User Processing* PID:18264 Kill:1 User:xxxxx VM:538(MB) EXE:/usr/local/lsws/fcgi-bin/lsphp-5.4.42 CMD:lsphp5

این یعنی باید فرایند LSPHP را در CSF/LFD مجاز اعلام کنیم تا جلوی وقوع این اتفاق را بگیریم.

برای انجام این کار، باید دستور زیر را اجرا کنیم:

sudo echo “pexe:/usr/local/lsws/fcgi-bin/lsphp.*” >> /etc/csf/csf.pignore

sudo csf -r; sudo service lfd restart

FORK BOMB

در مواردی نادر، LSPHP توسط PT_FORKBOMB و به‌خاطر داشتن تعداد زیادی فرایند نابود می‌شود! در عوض این کار، فرستادن سیگنال 9/SIGKILL به فرایند اصلی Litespeed را متوقف می‌کند. برای جلوگیری از متوقف‌سازی فرایندهای Litespeed توسط CSF/LFD، باید تنظیمات زیر را در /etc/csf/csf.conf اعمال کنید:

PT_LIMIT - Default: 10
PT_USERPROC - Default: 10
PT_FORKBOMB - Default: 0
PT_INTERVAL - Default 60

از آنجایی که هر مورد با دیگری فرق می‌کند، اعمال این تنظیمات برای هر مورد باید به‌صورت جداگانه انجام شود. مقادیر باید تا زمانی که مشکل متوقف شود به آهستگی افزایش پیدا کنند. برای اینکه تغییر تنظیمات اثر کنند، باید هم CSF و هم LFD را Restart کنید. این کار هم می‌تواند از طریق یک افزونه WHM یا از طریق ترمینال و با کمک دستور زیر انجام شود:

$ sudo csf -r; sudo service lfd restart

Extension Mismatch

استفاده از افزونه‌های LSPHP که با نسخه LSPHP شما سازگار نیستند، می‌توانند منجر به خطای 503 شوند. اگر دلیل خطای 503 همین باشد، پیام زیر را داخل یک لاگ stderr.log خواهید دید:

Warning: PHP Startup: imap: Unable to initialize module
Module compiled with module API=20090626
PHP    compiled with module API=20100525
These options need to match in Unknown on line 0

برای رفع این مشکل، باید ماژول یا PHP را از نو بسازید! از نسخه‌ای از PHP استفاده کنید که با ماژول سازگاری داشته باشد. همچنین اطمینان حاصل کنید که افزونه در مسیر درست نصب شده است.

Extension Loading Order

در صورت استفاده از PHP، برخی از افزونه‌ها به افزونه‌های دیگری نیاز دارند تا به ترتیب بارگذاری شوند و بتوانند بهترین عملکرد را ارائه کنند. این کار با تغییر فایل .ini از mysql.so به 20-mysql.so انجام می‌شود.

۲۰- الویت بارگذاری را مشخص می‌کند. این عدد می‌تواند بین ۱ تا ۹۹ متغیر باشد.

اگر دلیل بروز خطا همین باشد، باید پیغام زیر را در لاگ stderr.log مشاهده کنید:

PHP Warning:  PHP Startup: Unable to load dynamic library

Open Files Limit

اگر پیغام زیر را در لاگ وب‌سرورتان دیدید، یعنی سیستم‌تان به نهایت مقدار فایل‌های باز ممکن رسیده است:

[INFO] [319934] [1.1.1.1:49873-1#APVH:lsapi] connection to [uds://tmp/lshttpd/APVH-php56.sock] on request #0, confirmed, 0, associated process: 0, running: 0, error: Too many open files!

برای بررسی محدودیت فعلی، دستور زیر را اجرا کنید:

$ sudo ulimit -n

خروجی این دستور، محدودیت کنونی سیستم‌تان را نشان می‌دهد. برای رفع مشکل ۵۰۳ باید این محدودیت را با اجرای دستور زیر افزایش دهید:

$ sudo ulimit -n <Increased_Number>

حالا احتمالاً دیگر مشکل 503 از بین خواهد رفت؛ چراکه LSPHP می‌تواند فایل‌های بیشتری را در سیستم باز کند.

Resource temporarily unavailable

اگر از WordPress استفاده می‌کنید، احتمالاً هنگام کار با تصاویر گرافیکی با این خطا مواجه خواهید شد:

libgomp: Thread creation failed: Resource temporarily unavailable

اگر از WordPress استفاده می‌کنید، احتمالاً هنگام کار با تصاویر گرافیکی با این خطا مواجه خواهید شد:

حتما بخوانید:  htaccess چیست؟ چگونه از آن برای SEO تکنیکال استفاده کنیم؟

معمولاً این مشکل به‌ خاطر ماژول ImageMagick ایجاد می‌شود. این ماژول به استفاده از منابع به‌میزان زیاد مشهور است. برای رفع مشکل، میزان memory_limit را در فایل php.ini افزایش دهید، یا محدودیت حافظه خارجی app را به میزان بالاتری مثل 8G افزایش دهید.

Strace

از دستور زیر برای رصد کردن فرایندهای PHP استفاده کنید تا بفهمید چه اتفاقاتی در جریان هستند:

strace -tt -T -f -p <pid>

این دستور مشخص می‌کند که PHP چه می‌کند و مشکل کجا قرار دارد.

برای مثال، داخل لاگ وب‌سرور ممکن است ورودی لاگ زیر را ببینید:

[INFO] [1.1.1.1:48506] connection to [/tmp/lshttpd/APVH_vhost_Suphp.sock] on request #0, confirmed, 1, associated process: 791228, running: 1, error: Connection reset by peer!

اینجا می‌توانیم ID فرایند را از associated process: 791228  بگیریم و رصد کردن را با کمک دستور زیر اجرا کنیم:

strace -tt -T -f -p 791228

نکته: در برخی مواقع، پیدا کردن آیدی PHP خیلی آسان نیست؛ چراکه PHP با سرعت بسیار بالا اجرا می‌شود.

در چنین شرایطی،سعی کنید آیدی والد را رصد کنید. عیب رصد کردن آیدی والد در این است که امکان دارد اطلاعات نامرتبط دریافت کنید. همین موضوع باعث می‌شود که مکان‌یابی مشکل پیچیده شود.

یک راه‌حل این است که از اسکریپت آیدی PHP را استخراج کرد. این کار هم به این بستگی دارد که کدام کاربر SuEXEC از PHP استفاده می‌کند و اینکه کدام اسکریپت اجرا می‌شود.

while true; do if mypid=`ps aux | grep $USERNAME | grep lsphp | grep $SCRIPTNAME | grep -v grep | awk '{print $2; }' | tail -1`; then strace -tt -T -f -p $mypid; fi ; done

توجه داشته باشید که $USERNAME باید با یوزرنیم اصلی و $SCRIPTNAME باید با اسکریپتی که در حال اجرا است جایگزین شوند.

ENABLE CORE FILES

در این بخش فرض می‌گیریم که قبلاً core dumpها را برای سنتوس و اوبنتو فعال کرده‌اید:

  • به کنسول ادمین سایت‌تان بروید و داخل آن شوید.
  • بعد از ورود، به Cofiguration بروید و سپس وارد Server ‌شوید. در مرحله آخر هم روی PHP کلیک کنید.
  • حالا روی Edit برای PHP Handler Defaults کلیک کنید.
  • تنظیمات زیر را اعمال کنید و سپس روی Save کلیک کنید.

Environment: LSAPI_ALLOW_CORE_DUMP=1

  • حالا که همه‌چیز آماده است، به قسمت Actions بروید و روی آیکونی که کنار Restart Detached PHP Process کلیک می‌کنید. در مرحله بعدی هم Apply Changes / Graceful Restart.
ANALAYZE CORE FILES

GNU Debugger یا GDB از خط gdb <path/to/lsphp/binary> <path/to/core/file>. استفاده می‌کند.

<path/to/lsphp/binary>  مسیری است که PHP binary در آن قرار دارد و برنامه‌های PHP از آن استفاده می‌کنند. مسیر منتهی به Core File، مکانی است که Core File در آن قرار دارد.

ابتدا برای لود کردن GDB باید ` را اجرا کنید.

سپس یک prompt همراه با gdb خواهید دید. در محله بعدی هم باید bt را بنویسید و enter را بزنید.

انجام این کارها، خروجی‌ای مثل خروجی زیر ایجاد خواهد کرد:

gdb <path/to/lsphp/binary> <path/to/core/file>
Program received signal SIGSEGV, Segmentation fault.
0x000000000061c91b in ?? ()
(gdb) bt
#0 0x000000000061c91b in ?? ()
#1 0x0000000000641ac3 in zend_stack_push ()
#2 0x000000000060bbf9 in ?? ()
#3 0x0000000000611515 in lex_scan ()
#4 0x000000000061fb60 in ?? ()
#5 0x0000000000608223 in ?? ()
#6 0x0000000000614965 in compile_file ()
#7 0x00007fd3c99eda21 in ?? () from /opt/alt/php55/usr/lib64/php/modules/phar.so
#8 0x00007fd3d0993359 in ?? () from /opt/alt/php55/usr/lib64/php/modules/opcache.so
#9 0x00007fd3d0994187 in ?? () from /opt/alt/php55/usr/lib64/php/modules/opcache.so
#10 0x00000000006b54da in ?? ()
#11 0x00000000006b68e8 in execute_ex ()
#12 0x000000000064239c in zend_execute_scripts ()
#13 0x00000000005e2fb0 in php_execute_script ()
#14 0x00000000006f29ff in ?? ()
#15 0x00000000006f2c5c in ?? ()
#16 0x00000000006f2f85 in ?? ()
#17 0x00007fd3d37cdd1d in __libc_start_main () from /lib64/libc.so.6
#18 0x0000000000424bc9 in _start ()

در این خروجی برخی از ماژول‌هایی را می‌بینیم که هنگام کرش شدن، در phar.so و opache.so بارگذاری می‌شوند. اگر قصد عیب‌یابی این مورد را دارید، باید phar.so و opache.so را غیرفعال کنید تا بفهمید کدام ماژول‌ها منجر به این خطا شده‌اند.

حتی امکان بررسی دقیق‌تر فایل core هم وجود دارد. این کار در پیدا کردن عمکردی که منجر به ایراد شده موثر است. برای فهمیدن این موضوع، دستور زیر را اجرا کنید:

(gdb) frame 13
(gdb) print (char *)(executor_globals.function_state_ptr->function)->common.function_name
(gdb) print (char *)executor_globals.active_op_array->function_name
(gdb) print (char *)executor_globals.active_op_array->filename

حتی اگر پاسخ یک صفحه خالی هم باشد مشکلی ندارد. آنقدر اجرای این دستور را ادامه دهید تا عمکلرد یا فایل مخرب را پیدا کنید..