En resumen: FrankenPHP es un servidor de aplicaciones basado en Caddy que integra PHP en su propio programa. Para la seguridad de FrankenPHP tras PHP2Shell eso significa: no cuentan los paquetes de PHP de la distribución, sino la versión de PHP del binario de FrankenPHP o de la imagen de contenedor. Compile o descargue una versión con PHP corregido y reinicie todos los workers.
Por qué FrankenPHP se parchea de otra manera
En las configuraciones clásicas, la distribución entrega PHP como paquete y una actualización sustituye los archivos. FrankenPHP, en cambio, contiene PHP como biblioteca integrada. Quien usa el binario oficial o una imagen de contenedor basada en él recibe PHP incluido. Un apt upgrade en el host no cambia nada al respecto.
PHP2Shell comprende CVE-2026-109618 y CVE-2026-109619, cada una con un CVSS v4.0 de 9,2. El proyecto PHP cita expresamente a FrankenPHP entre los modos de funcionamiento afectados. Están corregidas PHP 8.5.12, 8.4.27, 8.3.36 y 8.2.35. Lo decisivo es, por tanto, con qué versión de PHP se compiló su FrankenPHP.
Modo worker y PHP2Shell
FrankenPHP puede ejecutar aplicaciones en modo worker. En él, la aplicación se carga una vez y procesa después muchas solicitudes seguidas en el mismo proceso. Esto aporta velocidad, pero alarga la vida de cada proceso.
CVE-2026-109619 describe un estado interno de una solicitud que puede persistir tras liberar la memoria; una solicitud posterior en el mismo worker puede aprovecharlo antes de que se restablezca. En el modo worker, la interacción de muchas solicitudes en un proceso es lo normal. Eso no es motivo para renunciar al modo worker, pero sí un motivo claro para ejecutar con especial cuidado las actualizaciones y los reinicios. Los detalles técnicos están en CVE-2026-109619.
Seguridad de FrankenPHP: comprobar la versión
Compruebe la versión de PHP integrada directamente en el sistema en funcionamiento. Los comandos siguientes solo leen; los nombres de servicios y contenedores son ejemplos.
# Binario instalado
frankenphp version
# En el contenedor en ejecución (nombre del contenedor a modo de ejemplo)
docker exec app frankenphp version
docker exec app php -v
# ¿Qué imagen se está ejecutando realmente? (el digest muestra el estado exacto)
docker inspect --format '{{.Image}} {{.Config.Image}}' app
Anote la versión de PHP que muestre la salida. Si es anterior a las versiones corregidas, el sistema es vulnerable. Compruebe siempre el contenedor en ejecución, no solo la última imagen compilada, porque una imagen nueva solo surte efecto tras sustituir los contenedores.
Instalar la actualización y reiniciar todos los workers
Cómo es la actualización depende de su instalación:
- Binario en el host: instalar una nueva versión de FrankenPHP con la versión corregida de PHP y reiniciar el servicio.
- Contenedor: obtener la imagen base con la versión corregida de PHP, recompilar la imagen propia sin caché para la capa base y sustituir el contenedor.
- Compilado por su cuenta: recompilar con la versión corregida de PHP y regenerar todas las extensiones con la misma versión.
# Ejemplo de instalación en el host como servicio de systemd
systemctl restart frankenphp
# Ejemplo con Docker Compose: recompilar sin caché y sustituir el contenedor
docker compose build --pull --no-cache
docker compose up -d --force-recreate
Después, vuelva a comprobar la versión de PHP en el contenedor en ejecución y la hora de inicio de los procesos. En el modo worker, todos los workers deben haberse reiniciado. En Kubernetes hay pasos adicionales, descritos en Parchear PHP en Kubernetes; para contenedores en general, en Parchear PHP en contenedores Docker.
Una etiqueta como latest o una versión principal en el nombre de la imagen no garantiza que tenga la versión más reciente. Descargue de nuevo la imagen base de forma activa y compruebe después la versión de PHP en el contenedor en ejecución.
Medidas provisionales y refuerzo
Si la actualización no puede hacerse de inmediato, php.net recomienda medidas provisionales que no ofrecen una protección completa. En FrankenPHP se fijan los valores en el php.ini que carga FrankenPHP o mediante los ajustes de PHP en la configuración de Caddy, no con ini_set() en la aplicación.
; php.ini en el contenedor o en el host
session.upload_progress.enabled = 0
post_max_size = 8M
upload_max_filesize = 6M
Con función de carga de archivos, php.net indica post_max_size = 32M. En PHP 8.5 se añade fatal_error_backtraces=0. El límite de memoria corresponde al nivel del contenedor, por ejemplo mediante el límite de memoria del contenedor, y no a RLIMIT_AS ni RLIMIT_DATA. Tras cada cambio, reinicie todos los workers.
Para el funcionamiento continuo merece la pena referenciar las imágenes con un digest fijo, recompilarlas de forma automatizada con regularidad e incorporar un escáner de imágenes a la cadena de compilación. Además, un parche no elimina el software malicioso introducido antes. Conserve los registros desde el 20/10/2026; en el caso de los contenedores, eso significa guardarlos antes de sustituirlos.
Quien use FrankenPHP como binario compilado de forma estática debe saber que en él, además de PHP, están integradas de forma fija todas las extensiones. Una actualización significa por eso siempre sustituir todo el binario. Tras el cambio, compruebe la versión y la lista de extensiones cargadas para ver si todo sigue disponible como antes, y pruebe la aplicación antes de descartar la versión anterior. En entornos de contenedores se recomienda marcar cada imagen con la fecha de compilación. Así puede reconstruir en cualquier momento qué versión funcionó y cuándo y, en caso de duda, volver atrás de forma selectiva sin caer de nuevo en una versión vulnerable. Deje constancia en su documentación de la asignación de imagen, versión de PHP y momento.
¿Cómo ayuda PHP SOS en concreto?
- Comprobamos qué versión de PHP llevan realmente sus binarios de FrankenPHP y sus contenedores en ejecución.
- Mediante el servicio de parcheo de PHP recompilamos imágenes, sustituimos contenedores y reiniciamos todos los workers, con prueba documental.
- Conservamos los registros antes de la sustitución y revisamos la aplicación en busca de rastros.
- Para el funcionamiento continuo configuramos recompilaciones automatizadas y comprobaciones de imágenes dentro del refuerzo de servidores.
Preguntas frecuentes
¿Ayuda una actualización con apt o dnf en FrankenPHP?
Solo si el propio FrankenPHP procede de esos repositorios de paquetes y está compilado con el PHP parcheado. A menudo PHP está integrado de forma fija en el binario de FrankenPHP o en la imagen de contenedor. Entonces debe actualizar el binario o la imagen.
¿Por qué es especialmente importante el modo worker con PHP2Shell?
En el modo worker, la aplicación permanece en memoria y procesa muchas solicitudes seguidas en el mismo proceso. CVE-2026-109619 afecta justamente al estado interno que puede persistir entre solicitudes en el mismo worker. Por eso es obligatorio reiniciar todos los workers después de la actualización.
¿Cómo compruebo qué versión de PHP lleva FrankenPHP?
El binario de FrankenPHP muestra la versión de PHP integrada al consultar la versión. En un contenedor puede ejecutar el comando con docker exec. Asegúrese de comprobar la versión en el contenedor que realmente está en marcha, no en la imagen recién compilada.
¿Hay medidas provisionales específicas para FrankenPHP?
Valen las indicaciones generales de php.net. Los valores se fijan en el php.ini que carga FrankenPHP o en la configuración de PHP del archivo de Caddy, no mediante ini_set() en la aplicación. Después hay que reiniciar todos los workers.