Linux

Apache 無響應/偶爾停止

  • May 12, 2017

我在 Debian GNU/Linux 8 (jessie) 上執行帶有 PHP 7.0 和 MySQL 5.5 的 Apache http server 2.4。有時,Apache 會在幾秒鐘內完全無響應 - 大約 30 秒或更長時間。在這個時候,請求似乎在排隊——當 Apache 終於重新開始正常工作時,很多堆積起來的請求必須一次處理,這當然也不是很好。

Apache 無響應的原因尚不清楚,因為:

  • CPU 負載完全下降;Apache、MySQL 或其他任何東西都不會顯著使用 CPU
  • Apache error_log 中沒有錯誤
  • MySQL 中沒有阻塞查詢 - 當我輸入“SHOW PROCESSLIST”時沒有顯示
  • 每秒一次,“內部虛擬連接”在 access_log 中可見
  • 伺服器上的總負載不能太高才能發生這種情況;即使負載低於平均水平且沒有多少使用者登錄我們的系統,也可能發生這種情況
  • 甚至包含 only 的 PHP 腳本echo "Hello World!";也不會執行
  • 在 PHP 中,沒有拋出 MySQL 錯誤,我可以輕鬆地從 MySQL 控制台執行 MySQL 語句
  • RAM 似乎沒問題 - 交換分區沒有被大量使用。這是top在攤位上說的:
KiB Mem:   6129344 total,  5975748 used,   153596 free,       24 buffers
KiB Swap:  1952764 total,   199428 used,  1753336 free.  4397256 cached Mem

我嘗試使用 strace 分析問題 - 準確地說,當我注意到伺服器變得無響應時,我在 shell 中輸入:

ps auxw | grep apache | awk '{print" -p " $2}' | xargs sudo strace

我觀察到的是,在此期間,在 strace 輸出中經常可以看到類似以下的行,但有時在不存在問題的情況下它們不會:

[pid 13521] fcntl(57, F_SETLK, {type=F_RDLCK, whence=SEEK_SET, start=1073741824, len=1}) = -1 EAGAIN (Resource temporarily unavailable)

通常,當沒有問題時,我可以看到如下行:

[pid  3414] fcntl(55, F_SETLK, {type=F_RDLCK, whence=SEEK_SET, start=1073741824, len=1}) = 0

有誰知道這意味著什麼?在我看來,存在某種鎖定衝突……

為了完整起見,這是我的 Apache 配置:

LogFormat "%h PID %P %l %u %t \"%r\" %s %b \"%{Referer}i\" \"%{User-agent}i\" %V" common
ServerTokens ProductOnly
ServerSignature Off
TraceEnable off

<IfModule mod_ssl.c>
   SSLHonorCipherOrder On
   SSLProtocol ALL -SSLv2 -SSLv3
   SSLCipherSuite EECDH+AES:AES256-SHA:AES128-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH:!EXP:!SRP:!DSS:!LOW;
   SSLVerifyClient none
   SSLVerifyDepth 1
   SSLInsecureRenegotiation Off
</IfModule>

ScriptAlias /cgi-bin52/ /usr/share/phpcgi/php52/
ScriptAlias /cgi-bin53/ /usr/share/phpcgi/php53/
ScriptAlias /cgi-bin54/ /usr/share/phpcgi/php54/
ScriptAlias /cgi-bin55/ /usr/share/phpcgi/php55/
ScriptAlias /cgi-bin56/ /usr/share/phpcgi/php56/
ScriptAlias /cgi-bin70/ /usr/share/phpcgi/php70/

Mutex flock

LoadModule deflate_module /usr/lib/apache2/modules/mod_deflate.so
LoadModule status_module /usr/lib/apache2/modules/mod_status.so

AcceptFilter http none
AcceptFilter https none

ExtendedStatus on
TimeOut 60
KeepAlive Off
MaxKeepAliveRequests 50
KeepAliveTimeout 2
Options Indexes MultiViews FollowSymLinks
MaxRequestWorkers 256
MaxRequestsPerChild 300

你看,已經有一個與鎖定行為相關的條目:Mutex flock……正如他所說,出於穩定性原因,它是由我的 Webhoster 預先配置的。此外,在https://httpd.apache.org/docs/2.4/mod/core.html#mutex,這似乎是少數幾個沒有任何問題的選項之一。

AcceptFilter在嘗試找到解決方案時添加了條目,但沒有成功。

誰能解釋我使用 strace 記錄的行是什麼fcntl ...意思,或者建議另一種分析問題的方法?

您可以查看strace阻塞的文件編號。當您執行操作時,ls -l /proc/$pid/fd您將看到該程序的所有打開文件。帶有文件號的符號連結將指向相關文件。

我見過這樣的問題,通常是會話文件有這個問題。如果它是會話文件,請讓您的開發人員了解session_write_close()PHP 中的功能以及省略session_write_close()對您在負載下的性能的影響。

fcntl 是試圖設置文件描述符的核心。您沒有關注的一件事是磁碟輸入/輸出等待時間,因此執行 iostat 或 mpstat 以查看在遇到問題時是否存在任何磁碟性能問題。

引用自:https://serverfault.com/questions/849705