Текуща ситуация: PHP2Shell. Две критични уязвимости в PHP (CVSS 9,2) позволяват злонамерен код без вход. Корекции от 21.10.2026 г.Какво да направите сега →

PHP-FPM, обяснен: мениджър на процесите, пулове и работни процеси

PHP-FPM изпълнява PHP като самостоятелна услуга с пулове и работни процеси. Как работи моделът на процесите, кои директиви са важни и защо работните процеси се рестартират след актуализации.

Актуалност 5 мин. четенеЗнания за PHP

Накратко: PHP-FPM (FastCGI Process Manager) изпълнява PHP като самостоятелна услуга до уеб сървъра. Главен процес управлява пуловете, а всеки пул стартира работни процеси, които обработват заявките през FastCGI. Пуловете могат да се използват за всеки уебсайт със собствен потребител, собствени ограничения и заключени настройки на PHP. Тъй като работните процеси обработват последователно много заявки, след актуализация на PHP всички те трябва да бъдат рестартирани.

Какво е PHP-FPM?

Ръководството на PHP описва FPM като основната реализация на FastCGI в PHP с функции, полезни най-вече за силно натоварени уебсайтове. FPM е приет с PHP 5.3.3 като самостоятелен SAPI, т.е. като самостоятелен режим на работа. Името му като SAPI е fpm-fcgi.

Разликата спрямо mod_php: PHP не работи в уеб сървъра, а като самостоятелна услуга. Nginx, Apache или друг уеб сървър предава PHP заявките през протокола FastCGI и получава готовия отговор. Така уеб сървърът и PHP могат да се рестартират, конфигурират и защитават независимо един от друг. Как принципно работи FastCGI, е описано в CGI и FastCGI.

Главен процес, пулове и работни процеси: моделът на процесите

PHP-FPM се състои от три нива:

  1. Главен процес: чете конфигурацията, отваря сокетите и стартира или прекратява работни процеси. Той самият не изпълнява код на приложение.
  2. Пулове: Всеки пул има име, собствен сокет или порт, собствен Unix потребител и собствени настройки на PHP. Ръководството изрично посочва различни uid, gid, chroot, среда и php.ini за всеки пул.
  3. Работни процеси: процеси на един пул, които приемат и изпълняват заявки. Един работен процес обработва последователно много заявки, преди да бъде заменен.

Колко работни процеси работят, определя мениджърът на процесите с директивата pm:

Режим Поведение Важни директиви
static фиксиран брой работни процеси pm.max_children
dynamic работни процеси между долна и горна граница pm.start_servers, pm.min_spare_servers, pm.max_spare_servers
ondemand работни процеси едва при нужда, премахване след бездействие pm.process_idle_timeout (по подразбиране 10s)

pm.max_children във всички режими ограничава броя на едновременните заявки. pm.max_requests заменя работен процес след фиксиран брой заявки; стойността по подразбиране 0 означава неограничено.

Кой режим е подходящ, зависи от натоварването. static държи винаги еднакъв брой работни процеси готови и е подходящ за равномерно натоварени приложения с достатъчно оперативна памет. dynamic е компромис за повечето уебсайтове. ondemand спестява памет на сървъри с много малки уебсайтове, защото пулове без посетители не заемат работни процеси; затова първата заявка след пауза отнема малко повече време. Прекалено висок pm.max_children може да докара сървъра до недостиг на памет при върхове в натоварването, прекалено нисък води до чакане и съобщения за грешки от уеб сървъра.

Пул с безопасни основни настройки

Пример за отделен пул за всеки уебсайт с директиви от ръководството на PHP. Пътищата и стойностите са примери:

; /etc/php/8.3/fpm/pool.d/kunde-a.conf
[kunde-a]
user = kunde-a
group = kunde-a

listen = /run/php/kunde-a.sock
listen.owner = www-data
listen.group = www-data
listen.mode = 0660

pm = ondemand
pm.max_children = 10
pm.process_idle_timeout = 10s

request_terminate_timeout = 60s
security.limit_extensions = .php
clear_env = yes

php_admin_value[open_basedir] = /var/www/kunde-a:/tmp
php_admin_flag[session.upload_progress.enabled] = off
php_admin_value[error_log] = /var/log/php/kunde-a.error.log

Според ръководството стойности чрез php_value и php_flag могат да се променят по време на изпълнение с ini_set(), а стойности чрез php_admin_value и php_admin_flag не могат. security.limit_extensions е по подразбиране .php .phar и определя кои разширения на файлове FPM изпълнява като основен скрипт. clear_env = yes е стойността по подразбиране и изчиства средата на работните процеси.

За наблюдение има страница със състоянието през pm.status_path и ping страница през ping.path. И двете трябва да са достъпни само вътрешно. Бавните заявки FPM записва с backtrace, когато са зададени request_slowlog_timeout и slowlog.

Важно

Ръководството на PHP предупреждава: който може да отвори FastCGI връзка към PHP-FPM, контролира конфигурацията на заявката и така може да изпълни произволен код. PHP-FPM никога не бива да е достъпен от недоверена мрежа. Ползвайте Unix сокет или listen.allowed_clients.

Каква роля играе PHP-FPM при PHP2Shell?

PHP-FPM е сред засегнатите режими на работа. Моделът на процесите проличава особено при CVE-2026-109619: вътрешно състояние, принадлежащо към заявката, може да остане след освобождаването на паметта и по-късна заявка в същия работен процес може да го използва, преди то да бъде нулирано. Това е възможно само защото работните процеси обработват много заявки последователно.

От това следват три задължения:

  1. Внасяне на актуализацията: PHP 8.5.12, 8.4.27, 8.3.36 или 8.2.35, респективно потвърден backport на дистрибуцията.
  2. Рестартиране на всички работни процеси: Новите файлове на диска не променят нищо, докато работят старите работни процеси. Това важи за всяка инсталирана версия на FPM и за всеки пул. Командите са описани в Рестартиране на PHP-FPM и на всички работни процеси.
  3. Заключване на временните стойности: Мерките от php.net, например session.upload_progress.enabled=0, се поставят в пула чрез php_admin_value или php_admin_flag, а не в .user.ini.

Разделянето на пулове не замества актуализацията, но ограничава щетите: ако всеки уебсайт работи под собствен потребител, атакуващият след пробив не достига автоматично файловете на останалите. Как изглежда това конкретно, описва Изолиране на PHP-FPM пулове за всеки уебсайт; включването в Nginx е описано в Защита на Nginx с PHP-FPM.

Как помага PHP SOS конкретно?

  • Установяване на пуловете: Изброяваме всички версии на FPM, пулове, потребители и сокети на Вашия сървър.
  • Корекция и рестартиране: Актуализираме PHP и доказваме чрез времената на стартиране, че вече не работи стар работен процес.
  • Разделяне на пуловете: В рамките на заздравяването на сървъра създаваме за всеки уебсайт пул със собствен потребител и заключени настройки.
  • Проверка на достъпността: Контролираме дали FastCGI сокетите и страниците със състоянието не са достъпни отвън.

Често задавани въпроси

Какво означава FPM?

FPM означава FastCGI Process Manager. Ръководството на PHP го описва като основната реализация на FastCGI в PHP с функции, полезни най-вече за силно натоварени уебсайтове. Приет е с PHP 5.3.3.

Каква е разликата между пул и работен процес?

Пулът е група от работни процеси с обща конфигурация: потребител, сокет, ограничения и настройки на PHP. Работният процес е отделен процес, който обработва последователно заявки. Един сървър може да има много пулове, например по един за всеки уебсайт.

Да бъде ли PHP-FPM достъпен през TCP или през Unix сокет?

Когато уеб сървърът работи на същия хост, ръководството на PHP препоръчва Unix сокет. При TCP трябва да се зададе listen.allowed_clients, защото иначе всеки адрес може да се свързва. Свободно достъпен FastCGI порт според ръководството позволява изпълнение на произволен код.

Защитава ли pm.max_requests от уязвимости като PHP2Shell?

Не. pm.max_requests заменя работен процес след фиксиран брой заявки и помага най-вече срещу изтичане на памет в разширения. Срещу уязвимост в интерпретатора помага само актуализацията с последващо рестартиране на всички работни процеси.

Източници

Незабавен контакт

Всеки час има значение. Пишете ни сега.

Опишете накратко системата, версията на PHP и какво сте забелязали. Ние се свързваме с Вас, уточняваме ситуацията и работим отдалечено, докато инцидентът бъде приключен и документиран.

Незабавна помощ