# Правилна настройка на memory_limit

> PHP memory_limit: какво прави стойността, къде важи, какво временно съветва php.net при PHP2Shell и какво важи отново след актуализацията.

Източник: https://phpsos.de/bg/blog/memory-limit-richtig-setzen/  
Актуалност: 25.10.2026  
Доставчик: PHP SOS, Спешна помощ за PHP и сигурност на сървъри. Незабавна помощ по WhatsApp: https://wa.me/491736494914?text=%D0%97%D0%B4%D1%80%D0%B0%D0%B2%D0%B5%D0%B9%D1%82%D0%B5%2C%20PHP%20SOS%2C%20%D0%B8%D0%BC%D0%B0%D0%BC%D0%B5%20%D0%BD%D1%83%D0%B6%D0%B4%D0%B0%20%D0%BE%D1%82%20%D0%BF%D0%BE%D0%BC%D0%BE%D1%89%20%D1%81%20%D0%BD%D0%B0%D1%88%D0%B8%D1%8F%20PHP%20%D1%81%D1%8A%D1%80%D0%B2%D1%8A%D1%80.%20%D0%A4%D0%B8%D1%80%D0%BC%D0%B0%3A%20%E2%80%A6%20%D0%A3%D0%B5%D0%B1%D1%81%D0%B0%D0%B9%D1%82%3A%20%E2%80%A6

**Накратко:** `memory_limit` определя колко памет може да заема една отделна PHP заявка; стойността по подразбиране е 128M. В нормална работа задавате краен размер, който подхожда на приложението, и го заключвате с `php_admin_value`. Докато PHP2Shell не е коригиран с пач, php.net временно съветва `memory_limit=-1`, което не може да се презаписва и е комбинирано с лимит чрез контейнер или cgroup, не чрез `RLIMIT_AS` или `RLIMIT_DATA`. След актуализацията отново важи краен размер.

## Рутинна настройка, която изведнъж е тема за сигурност

С години `memory_limit` беше регулатор за разработчиците. Ако един сайт съобщи „Allowed memory size exhausted", стойността се увеличава и проблемът е решен. С PHP2Shell това се превърна във въпрос на сигурност, а препоръката на php.net на пръв поглед изглежда парадоксална: за прехода собственият лимит на паметта на PHP трябва да отпадне изцяло.

Причината е CVE-2026-109618. Според проекта PHP състояние с недостиг на памет (Out-of-Memory) може да прекъсне PHP, докато данните на заявката са само частично инициализирани. Почистването на заявката може тогава да третира невалидни данни като валидни. Техническите подробности са в [CVE-2026-109618](https://phpsos.de/bg/php2shell/cve-2026-109618/), а какво се случва вътре в PHP при недостиг на памет, обяснява [memory_limit и Out-of-Memory](https://phpsos.de/bg/php/out-of-memory/). За операторите важи въпросът: коя стойност кога важи и къде трябва да стои?

## Какво дава memory_limit в нормална работа

Според ръководството на PHP `memory_limit` ограничава паметта, която един скрипт може да заема, и така защитава сървъра от зле написан код. Стойността по подразбиране е `128M`, а `-1` означава без лимит. Съкратени записи като `256M` или `1G` са позволени.

Две свойства са важни за сигурността. Първо, стойността може да се променя навсякъде, и по време на изпълнение чрез `ini_set()`. Много CMS и магазини сами я увеличават, например за импорти или обработка на изображения. Който иска да наложи стойност, трябва да я зададе с `php_admin_value`; според ръководството така зададени стойности не могат да се презаписват с `ini_set()`. Второ, ръководството препоръчва `memory_limit` да е по-голям от `post_max_size`.

Коя стойност подхожда, зависи от приложението. Погледът в лога за грешки показва дали се появяват съобщения за изчерпана памет и при кои извиквания. Доказало се е стойността да се задава за всеки сайт в собствения му FPM пул: по-щедра за магазин с импорти, по-пестелива за обикновена фирмена страница. Общо много висока стойност за всички сайтове пропилява защитния ефект, защото тогава една-единствена погрешна или злоупотребена заявка може да свърже много памет.

От PHP 8.5 има допълнително `max_memory_limit`. Тази настройка може да се задава само при стартиране и ограничава докъде изобщо може да се задава `memory_limit`. По-високите стойности се орязват с предупреждение. Стойността по подразбиране `-1` означава без горна граница.

## memory_limit след PHP2Shell: преходната мярка на php.net

За сървъри, които още не са актуализирани до 8.5.12, 8.4.27, 8.3.36 или 8.2.35 или до потвърден backport, php.net в съобщението за сигурност от 21.10.2026 г. посочва следните стъпки. Те намаляват риска на отделни пътища за атака, но според php.net не правят една инсталация сигурна:

1. **Задайте `memory_limit=-1`,** по възможност така, че приложенията да не могат да презапишат стойността, например с `php_admin_value` в пула на FPM или в конфигурацията на Apache.
2. **Проверете дали никъде не се задава отново краен лимит,** нито в друг пул, нито в директорийна конфигурация, нито в приложението.
3. **Задайте лимит на паметта чрез контейнер или cgroup,** като защита на наличността, по възможност така, че при надвишаване да се прекратява само засегнатият worker процес.
4. **Не използвайте `RLIMIT_AS` или `RLIMIT_DATA`.** Според php.net тези лимити могат да предизвикат точно уязвимата грешка при заявка за памет.

php.net обяснява, че `-1` премахва целенасочено предизвикваното достигане на границата на паметта на PHP, но грешка с паметта на по-ниско ниво все още може да достигне уязвимия път. Прегледът на всички преходни мерки е в [Незабавни мерки, когато още не можете да пачнете](https://phpsos.de/bg/php2shell/sofortmassnahmen-ohne-patch/).

```ini
; Пул на FPM, напр. /etc/php/8.3/fpm/pool.d/www.conf (само до актуализацията)
php_admin_value[memory_limit] = -1
```

```bash
# Къде навсякъде се задава memory_limit (само четене)
grep -rn 'memory_limit' /etc/php/ /etc/apache2/ 2>/dev/null
grep -rn --include='*.php' -E "ini_set\s*\(\s*['\"]memory_limit" /var/www | head -20
grep -rn --include='.user.ini' 'memory_limit' /var/www
```

Как да зададете лимита на cgroup за услугата FPM, описва [Задаване на лимити на паметта със systemd и cgroups](https://phpsos.de/bg/blog/speichergrenzen-systemd-cgroups/). Без този външен лимит една отделна заявка може да докара целия сървър до недостиг на памет.

> **Важно:**
> След всяка промяна рестартирайте всички PHP worker процеси. Работещият worker запазва старите си стойности.

## Какво важи след актуализацията

С коригираните версии според ръководството на PHP се е променило и поведението на `memory_limit`. От 8.5.12, 8.4.27, 8.3.36 и 8.2.35 той е мек лимит: заявка за памет, която го надвишава, в повечето случаи още може да бъде завършена, преди да се предизвика грешката. Нова настройка, `memory_hard_limit_percent`, определя твърд лимит, който никога не се надвишава.

| Настройка | Стойност | Ефект според ръководството |
|---|---|---|
| `memory_hard_limit_percent` не е зададен или `-1` | по подразбиране | твърд лимит двойно по-висок от `memory_limit` до 1G, над това `memory_limit` плюс 1G |
| `memory_hard_limit_percent = 150` | пример | при `memory_limit=128M` твърд лимит 192M |
| `memory_limit = -1` | без лимит | тогава няма и твърд лимит |

Ръководството посочва практическа точка за проверка: ако `memory_hard_limit_percent` не се разпознава, използваната версия на PHP е засегната и трябва да се актуализира. При backport корекции на дистрибуциите проверете допълнително състоянието през changelog на пакета.

```bash
# Познава ли двоичният файл на FPM новата настройка? (коригирайте номера на версията)
php-fpm8.3 -i | grep -E 'memory_hard_limit_percent|memory_limit'
```

След актуализацията `memory_limit=-1` е изпълнил целта си. Върнете се към крайна стойност, която подхожда на приложението, и я заключете с `php_admin_value`. Лимитът на cgroup може да остане като допълнителен защитен слой.

## Как помага PHP SOS конкретно?

- Установяваме къде на Вашия сървър се задава и презаписва `memory_limit`, включително от приложенията.
- Прилагаме преходните мерки на php.net на правилното място и добавяме лимит на cgroup за услугата FPM.
- Чрез [PHP пач услугата](https://phpsos.de/bg/leistungen/php-patch-service/) довеждаме PHP до коригирано състояние и рестартираме всички worker процеси.
- След това отново задаваме подходяща крайна стойност и документираме настройките.


## Често задавани въпроси

**Каква е стойността по подразбиране на memory_limit?**  
Според ръководството на PHP 128M. Стойността ограничава колко памет може да заема един отделен скрипт. Тя може да се променя в php.ini, в конфигурацията на сървъра, в пула на FPM и по време на изпълнение чрез ini_set(), стига да не е заключена с php_admin_value.

**Защо php.net съветва memory_limit=-1 при PHP2Shell?**  
Една от уязвимостите, CVE-2026-109618, е свързана със състоянието при недостиг на памет. Според php.net memory_limit=-1 премахва целенасочено предизвикваното достигане на границата на паметта на PHP, но не всяка грешка с паметта. Мярката не е пълна защита и трябва да се комбинира с лимит на паметта чрез контейнер или cgroup.

**Мога ли вместо това да задам лимита с ulimit?**  
Не. php.net изрично съветва да не се използват RLIMIT_AS или RLIMIT_DATA като заместител, защото тези лимити могат да предизвикат точно уязвимата грешка при заявка за памет. Препоръчва се лимит чрез контейнер или cgroup.

**Какво важи след актуализацията до коригирана версия на PHP?**  
Според ръководството в коригираните версии memory_limit е мек лимит, допълнен от твърд лимит чрез memory_hard_limit_percent. Преходната мярка със стойност -1 тогава е изпълнила целта си и трябва да важи отново краен, подходящ за приложението стойност.

## Източници

- [php.net: Съобщение за сигурност от 21.10.2026 г.](https://www.php.net/)
- [Ръководство на PHP: основни настройки (memory_limit)](https://www.php.net/manual/en/ini.core.php)
- [Ръководство на PHP: конфигурация на FPM](https://www.php.net/manual/en/install.fpm.configuration.php)
