Le symptôme est déroutant : le site devient inaccessible pendant quelques secondes à quelques minutes, puis repart tout seul, sans qu’aucune erreur ne remonte dans les journaux PHP ni dans ceux de WordPress. Ni debug.log, ni les journaux de nginx ou Apache ne donnent d’explication claire, à part une éventuelle erreur 502 côté serveur web au moment du plantage. Ce silence dans les logs applicatifs est en soi un indice : quand PHP-FPM meurt sans laisser de trace d’erreur, le noyau Linux est souvent en cause, via un mécanisme appelé OOM killer.
Comprendre ce mécanisme demande de sortir du réflexe habituel qui consiste à chercher la cause dans les journaux applicatifs. Le OOM killer opère un niveau plus bas, directement dans le noyau, et ne laisse aucune trace dans PHP pour la simple raison qu’il tue le processus avant même que celui-ci ait la moindre chance de se plaindre.
Ce que fait réellement le OOM killer
Quand la mémoire disponible sur un serveur (RAM plus swap éventuel) approche l’épuisement complet, le noyau Linux déclenche un mécanisme de dernier recours nommé Out-Of-Memory killer. Son rôle est de choisir un processus à sacrifier pour libérer de la mémoire avant que le système entier ne se bloque. Ce choix n’est pas aléatoire : chaque processus reçoit un score, le oom_score, calculé notamment à partir de sa consommation mémoire relative. Un processus PHP-FPM gourmand, en particulier lors d’un pic de trafic ou d’une requête mal optimisée qui charge trop de données en mémoire, devient rapidement la cible privilégiée.
Retrouver la trace de l’incident
Le seul endroit où l’incident laisse une trace explicite est le journal noyau, consultable via dmesg ou directement dans les journaux système :

dmesg -T | grep -i "killed process"
[Sun Jan 14 14:52:03 2024] Out of memory: Killed process 18432 (php-fpm)
total-vm:612344kB, anon-rss:498212kB, file-rss:0kB, shmem-rss:0kB,
UID:33 pgtables:1024kB oom_score_adj:0
Cette ligne confirme sans ambiguïté que le processus PHP-FPM portant le PID 18432 a été tué par le noyau, avec une empreinte mémoire réelle (RSS) proche de 500 Mo au moment de sa mort. C’est la preuve définitive que le problème n’est pas applicatif au sens d’un bug PHP, mais bien une saturation mémoire globale du serveur.
Pourquoi la mémoire se sature
Plusieurs causes se combinent généralement sur un serveur WordPress :
- Un nombre de processus enfants PHP-FPM (
pm.max_children) mal dimensionné par rapport à la mémoire réellement disponible, chaque processus pouvant consommer plusieurs dizaines à plusieurs centaines de mégaoctets selon les plugins actifs. - Un pic de trafic soudain (campagne emailing, passage dans un média) qui multiplie les processus simultanés bien au-delà du niveau habituel.
- Une requête ou un import particulièrement gourmand (génération de rapport, traitement d’image en masse) qui fait exploser la mémoire d’un seul processus.
- L’absence totale de swap, qui prive le système de la moindre marge de manœuvre avant de devoir tuer un processus.
| Facteur | Effet sur le risque OOM |
|---|---|
| pm.max_children trop élevé | Augmente fortement le risque |
| Absence de swap | Supprime la marge avant intervention du OOM killer |
| Cache d’objets externe (Redis, Memcached) | Réduit la mémoire consommée par processus PHP |
Diagnostiquer le bon dimensionnement
Avant de modifier quoi que ce soit, il faut mesurer la consommation réelle moyenne d’un processus PHP-FPM sur ce site précis, plutôt que de copier une valeur générique trouvée en ligne :
ps --no-headers -o "rss,cmd" -C php-fpm8.2 | awk '{ sum+=$1 } END { print sum/NR/1024 " Mo par processus en moyenne" }'
Sur ce cas, la moyenne mesurée tournait autour de 85 Mo par processus, avec des pics ponctuels dépassant 400 Mo lors de la génération de miniatures d’images en masse. Un pm.max_children fixé à 50 sur un serveur disposant de 4 Go de RAM totale, partagée avec MariaDB et nginx, laissait une marge insuffisante en cas de pic simultané.
Le OOM killer n’est pas le bug : c’est le pompier qui arrive après l’incendie. Le vrai travail consiste à dimensionner en amont pour qu’il n’ait jamais besoin d’intervenir.
Réduire le risque durablement
Trois leviers combinés réduisent nettement la fréquence de ces incidents : abaisser pm.max_children à une valeur cohérente avec la mémoire réellement disponible, activer un peu de swap comme filet de sécurité (pas comme mémoire principale), et alléger la consommation par processus en déportant le cache d’objets vers Redis plutôt que de le garder en mémoire PHP locale. Il vaut mieux surveiller dmesg en continu via la supervision plutôt que de découvrir l’incident après coup par un client mécontent.
En résumé
Un plantage silencieux de PHP-FPM sans erreur applicative pointe presque toujours vers le OOM killer du noyau Linux, visible uniquement dans les journaux système via dmesg, jamais dans les logs PHP. Le traitement de fond ne consiste pas à réagir à chaque kill, mais à dimensionner pm.max_children et la mémoire disponible du serveur pour que le noyau n’ait jamais besoin de trancher à la place de l’administrateur.