How can we help?

PHP CVE-2026-109618 and CVE-2026-109619 manual fixes

Follow

On 21 October 2026 the PHP project published two critical vulnerabilities, CVE-2026-109618 and CVE-2026-109619, that can allow remote code execution on a web server without logging in. We wrote more about the incident on our website here: https://www.smseagle.eu/security-advisory/security-advisory-critical-vulnerabilities-in-php-cve-2026-109618-cve-2026-109619/

This article explains how to change the configuration of your SMSEagle gateway to reduce that risk until the gateway receives an updated PHP package.

The only complete fix for CVE-2026-109618 and CVE-2026-109619 is an updated PHP package. SMSEagle software 7.0.2 and newer includes updated PHP packages with the fix, so the recommended solution is to update your gateway to version 7.0.2 or newer.

The changes described in this article are an interim measure for gateways that cannot be updated to 7.0.2 yet. They close the attack paths confirmed by the PHP project and make the remaining ones harder to use, but they do not remove the vulnerabilities from PHP itself.

The changes affect only the PHP, Apache and systemd configuration. They do not change any SMSEagle data or settings. A copy of every changed file is kept, so the changes can be undone at any time.

What changes for users

  • Requests larger than 32 MB are rejected. Uploads of voice models, patches, backups and firmware still accept up to 300 MB.
  • The web interface and the API restart once, for a few seconds.

Before you start

  • You need SSH access to the gateway as root.
  • Each grey box contains one command. Copy and run them one by one, in order, in the same terminal session. Step 1 stores the backup location in a variable that later steps use.
  • Do not apply the changes while a backup is being restored or a report is being exported. The restart in step 6 interrupts them.
  • Instead of running the commands yourself, you can install the patch file patch-20261021-php.bin in the web interface. It makes exactly the same changes. See Optional: install the patch file instead. Use only one of the two methods.

Apply the changes manually

Step 1. Back up the files that will change

Copies the original PHP, Apache and systemd configuration files into a new folder under /etc, keeping their full paths. The last command prints the folder name. Write it down: you need it if you ever want to undo the changes.

shopt -s nullglob
BACKUP=/etc/patch-20261021-php-backup-$(date +%Y%m%d-%H%M%S)
mkdir -p "$BACKUP"
cp -a --parents /etc/php/*/fpm/php.ini /etc/php/*/apache2/php.ini /etc/php/*/cgi/php.ini /etc/php/*/fpm/pool.d/*.conf /etc/systemd/system/php*-fpm.service.d/override.conf /etc/apache2/apache2.conf "$BACKUP/"
echo "$BACKUP"

Step 2. Change the PHP settings

Sets three values in every php.ini used by the web interface, replacing the existing or commented-out line in place:

  • session.upload_progress.enabled = 0 switches off the session upload progress feature, the confirmed attack path of CVE-2026-109619. The SMSEagle web interface does not use it.
  • memory_limit = -1 removes the PHP memory limit, so that a request cannot hit the out-of-memory error behind CVE-2026-109618. Step 5 adds a memory cap for the whole service instead.
  • max_input_nesting_level = 32 limits how deeply nested form field names can be (default 64). SMSEagle forms use at most 5 levels.
for f in /etc/php/*/fpm/php.ini /etc/php/*/apache2/php.ini /etc/php/*/cgi/php.ini; do sed -i -e 's/^;\?\s*session\.upload_progress\.enabled\s*=.*/session.upload_progress.enabled = 0/' -e 's/^;\?\s*memory_limit\s*=.*/memory_limit = -1/' -e 's/^;\?\s*max_input_nesting_level\s*=.*/max_input_nesting_level = 32/' "$f"; echo "updated $f"; done

Step 3. Lock the settings in the PHP-FPM pools

Applies only to gateways where PHP runs as PHP-FPM. To check, run:

systemctl list-units 'php*-fpm.service' --no-legend

If it prints a line such as php8.1-fpm.service loaded active running, the gateway uses PHP-FPM: run the commands below. If it prints nothing, PHP runs inside Apache and you can skip to step 4. Running the commands below on such a gateway is also safe: they print nothing and change nothing.

The commands add the same three settings to every PHP-FPM pool as php_admin values, which the application cannot change at run time. The API pool also gets a 32 MB request size limit, because the API does not accept file uploads.

for f in /etc/php/*/fpm/pool.d/*.conf; do printf '%s\n' "php_admin_flag[session.upload_progress.enabled] = off" "php_admin_value[memory_limit] = -1" "php_admin_value[max_input_nesting_level] = 32" >>"$f"; echo "updated $f"; done
for f in /etc/php/*/fpm/pool.d/api.conf; do printf '%s\n' "php_admin_value[post_max_size] = 32M" "php_admin_value[upload_max_filesize] = 30M" >>"$f"; done

Step 4. Limit the request size in Apache

Adds these lines to the end of /etc/apache2/apache2.conf (each quoted part of the command becomes one line in the file):

  • A request that declares a body larger than 32 MB is rejected by Apache with HTTP 403 before PHP receives it. This is the <If> block, and it is what protects gateways where PHP runs as PHP-FPM.
  • LimitRequestBody applies the same 32 MB limit where Apache reads the request itself (static files, and PHP running inside Apache). It rejects larger requests with HTTP 413.
  • The upload pages for voice models, patches, backup restore and firmware accept up to 300 MB.
  • On gateways where PHP runs inside Apache (mod_php), the memory limit is locked so the application cannot change it.
printf '%s\n' 'LimitRequestBody 33554432' '<LocationMatch "^/(index\.php/)?(settings/calls/voices/upload|system/patches/upload|system/backup/restore|calls/upload_voice|kalkun/upload/patch|kalkun/upload/update|kalkun/restore_backup)(/.*)?$">' 'LimitRequestBody 314572800' '</LocationMatch>' '<If "%{HTTP:Content-Length} -gt 33554432 && ! %{REQUEST_URI} =~ m#^/(index\.php/)?(settings/calls/voices/upload|system/patches/upload|system/backup/restore|calls/upload_voice|kalkun/upload/patch|kalkun/upload/update|kalkun/restore_backup)(/.*)?$#">' 'Require all denied' '</If>' '<IfModule php7_module>' 'php_admin_value memory_limit -1' '</IfModule>' '<IfModule php_module>' 'php_admin_value memory_limit -1' '</IfModule>' >>/etc/apache2/apache2.conf

Step 5. Cap the memory used by PHP

Because step 2 removes the PHP memory limit, this step limits all PHP-FPM processes and all Apache processes to half of the gateway's memory. If one request uses too much memory, the system stops only that process and the web interface keeps running. OOMPolicy=continue keeps the service running after such an event. Older systems (systemd before version 243) ignore that line, which is harmless.

MEM=MemoryLimit
[ "$(stat -fc %T /sys/fs/cgroup)" = "cgroup2fs" ] && MEM=MemoryMax
for f in /etc/systemd/system/php*-fpm.service.d/override.conf; do printf '%s\n' "$MEM=50%" "OOMPolicy=continue" >>"$f"; done
mkdir -p /etc/systemd/system/apache2.service.d
printf '%s\n' "[Service]" "$MEM=50%" "OOMPolicy=continue" >/etc/systemd/system/apache2.service.d/override.conf

Step 6. Check the configuration and restart

The first command must print Syntax OK. If it prints an error, do not run the next commands. Restore the backup as described in How to undo the changes. The restart interrupts the web interface and the API for a few seconds.

apache2ctl -t
systemctl daemon-reload
systemctl try-restart 'php*-fpm.service' apache2.service

Continue with Verify the changes.

Optional: install the patch file instead

The patch file patch-20261021-php.bin makes exactly the same changes as the manual steps above, including the backup. Use it instead of the manual steps, not in addition to them.

  1. Download patch-20261021-php.bin and save it on your computer. Do not unpack or rename it.
  2. Log in to the gateway web interface as an administrator and open the patches page:
    • Software 7.0.0 and newer: System > Patches in the menu.
    • Software older than 7.0.0: the page is not in the menu. Type its address in the browser: https://<gateway address>/patches, for example https://192.168.1.101/patches.
  3. In Patch file for manual install select patch-20261021-php.bin and click Upload.
  4. Click Install now and confirm with Install. The page shows the installation output line by line. Do not power off or unplug the gateway during the install. The output ends with Patch applied, original files saved in /etc/patch-20261021-php-backup-…. Write down that folder name: you need it if you ever want to undo the changes.
  5. About 10 seconds after the install, the web server and PHP restart and the page stops responding for a moment. The page does not reload by itself. Wait about 30 seconds, refresh the page and log in again.

Verify the changes

Run these commands over SSH:

head -c 40M /dev/zero | curl -sk -o /dev/null -w '%{http_code}\n' --data-binary @- https://127.0.0.1/
tail -n 1 /var/log/apache2/error.log
systemctl is-active apache2 'php*-fpm'
  • The first command sends a 40 MB request to the gateway. It must print 403 or 413.
  • The second command shows the last Apache error log entry. It must contain client denied by server configuration. Together with the first result, this shows that Apache rejected the request before PHP received it. A 403 without that log entry comes from the web application, which means the limit is not active.
  • The third command must print active for Apache and, if present, for PHP-FPM.

Then open the web interface and log in to confirm it works.

How to undo the changes

This works for both methods and needs SSH access as root. Use the backup folder name you wrote down: the patch prints it at the end of the install, and the manual procedure prints it in step 1. After the patch install the folder also contains a README.txt that lists every file and where it belongs.

Replace YYYYMMDD-HHMMSS below with the date and time from the folder name. The commands remove the file that step 5 created, copy the original files back and restart the gateway.

cd /etc/patch-20261021-php-backup-YYYYMMDD-HHMMSS
rm -f /etc/systemd/system/apache2.service.d/override.conf
cp -a etc/. /etc/
reboot
Was this article helpful?
0 out of 0 found this helpful