Le due vulnerabilità critiche PHP2Shell hanno fatto emergere un problema che molti amministratori di sistema conoscono bene, ma che raramente riceve la giusta attenzione: come individuare tutte le installazioni di PHP presenti nell’infrastruttura aziendale, comprese quelle che nessuno ricorda di aver installato? L’aggiornamento straordinario del 21 ottobre 2026, necessario per correggere due falle che consentono l’esecuzione di codice da remoto (RCE), ha trasformato una questione di inventario software in una vera emergenza di sicurezza.
Secondo le rilevazioni di W3Techs aggiornate al 21 ottobre 2026, PHP è utilizzato dal 69,3% dei siti Web per i quali è possibile identificare il linguaggio di programmazione lato server. Un dato che conferma la straordinaria diffusione della tecnologia e rende particolarmente delicata la gestione delle vulnerabilità individuate nel motore PHP: aggiornare il CMS o i plugin non aiuta, in questo caso, a correggere il componente vulnerabile.
Molti professionisti e imprese possiedono server, appliance e applicazioni Web che sfuggono agli inventari ufficiali. E quando arriva una vulnerabilità critica, diventa difficile stabilire dove intervenire e con quale priorità.
PHP2Shell: perché non basta aggiornare i server Web conosciuti
Il team di sviluppo di PHP ha pubblicato un aggiornamento di sicurezza straordinario per correggere CVE-2026-109618 e CVE-2026-109619, entrambe classificate con un punteggio CVSS 4.0 pari a 9,2.
Le versioni corrette sono PHP 8.5.12, 8.4.27, 8.3.36, 8.2.35 e precedenti: le vulnerabilità interessano il motore del linguaggio e possono permettere a un aggressore non autenticato di eseguire codice sul server. Gli sviluppatori hanno indicato come potenzialmente esposte le installazioni che elaborano richieste Web attraverso PHP-FPM, Apache con mod_php, php-cgi, FrankenPHP e LiteSpeed.
Il rischio maggiore riguarda mod_php: il progetto PHP conferma infatti la disponibilità di una tecnica di attacco capace di raggiungere il codice vulnerabile prima che l’applicazione inizi a eseguire le proprie istruzioni.
Per gli approfondimenti tecnici sulle singole falle sono disponibili gli advisory GHSA-w8hw-w9fx-j79w e GHSA-6wmf-4rv5-p3rp: nel nostro articolo su PHP2Shell cerchiamo di dettagliare gli aspetti più importanti in un linguaggio un po’ più accessibile.
Il vero problema è il PHP nascosto dentro software e appliance
In molte aziende l’inventario dei server Web principali è relativamente aggiornato, mentre le applicazioni secondarie ricevono meno attenzione. Un servizio installato anni prima per esigenze amministrative può continuare a funzionare senza che il personale sappia esattamente quali componenti utilizzi.
Un esempio tipico è quello di un’applicazione fornita da un soggetto esterno che include Apache, PHP e un database nella propria directory di installazione. L’amministratore aggiorna regolarmente Windows o Linux, ma l’interprete PHP incorporato rimane alla versione distribuita originariamente dal fornitore.
Situazioni simili possono riguardare strumenti di gestione documentale, portali aziendali, interfacce amministrative, apparati che espongono un pannello Web e pacchetti software distribuiti come installazioni autonome.
Su Windows, in particolare, la presenza di file come php.exe e php-cgi.exe può segnalare un’installazione che non compare nell’elenco dei programmi tradizionalmente amministrati.
Su Linux, accanto ai pacchetti installati tramite apt, dnf o altri gestori possono esistere compilazioni personalizzate, installazioni sotto /opt, applicazioni distribuite in container Docker e runtime PHP gestiti separatamente rispetto ai classici repository.
Huntress, nella sua analisi delle vulnerabilità PHP2Shell, insiste sulla necessità di cercare gli interpreti incorporati nei prodotti di terze parti e nei pannelli di hosting come cPanel e Plesk: sono strumenti che aggiungono ulteriori modalità di distribuzione e gestione delle versioni PHP.
Come trovare tutte le installazioni PHP su Linux
Il primo controllo consiste nell’esaminare i pacchetti installati dal sistema operativo. Su Debian e Ubuntu si può utilizzare il comando dpkg -l 'php*'; sui sistemi basati su RPM, come RHEL e derivati, si può partire da rpm -qa | grep -i php.
Le informazioni ottenute aiutano a individuare i componenti gestiti dal package manager, ma non rappresentano un inventario completo: PHP potrebbe essere infatti presente all’interno di directory esterne oppure essere stato compilato manualmente e installato senza registrarlo nel database dei pacchetti.
Un secondo passaggio consiste quindi nella ricerca dei binari: il comando seguente permette di individuare numerosi eseguibili potenzialmente rilevanti. Non copre l’intero filesystem e non identifica tutte le possibili denominazioni, ma amplia sensibilmente il controllo rispetto alla semplice interrogazione dei pacchetti:
find /usr /opt /srv -type f \( -name 'php' -o -name 'php-cgi' -o -name 'php-fpm' \) 2>/dev/null
Una volta individuato un eseguibile, si può verificarne la versione tramite l’opzione -v, evitando però di avviare indiscriminatamente binari sconosciuti o non attendibili. In alcuni casi conviene esaminarne prima provenienza, firma, hash e dipendenze.
Come verificare quali processi PHP sono realmente in esecuzione
Va inoltre controllato quali processi PHP risultassero in esecuzione: comandi come ps aux | grep '[p]hp', l’ispezione delle unità systemd e l’esame della configurazione di Apache o Nginx consentono di distinguere una copia inutilizzata da un runtime che riceve richieste.
Su Linux, il comando systemctl list-units --type=service --all | grep -Ei 'php|apache|httpd|nginx' permette di individuare le unità systemd associate a PHP-FPM, Apache e Nginx, verificando quali servizi siano in esecuzione.
Apache e Nginx: individuare la versione PHP utilizzata dai siti
Com’è noto, Apache può eseguire PHP direttamente tramite mod_php oppure inoltrare le richieste a PHP-FPM attraverso SetHandler e ProxyPassMatch; Nginx, invece, utilizza generalmente la direttiva fastcgi_pass per comunicare con un processo PHP-FPM attraverso un socket Unix o una porta TCP.
Il comando apachectl -M aiuta a verificare il caricamento del modulo PHP in Apache, mentre nginx -T mostra la configurazione effettivamente caricata da Nginx, comprese le direttive presenti nei file inclusi.
Incrociando queste informazioni con i processi attivi e i socket in ascolto, è possibile stabilire quali interpreti PHP siano realmente collegati ai servizi Web, distinguendoli dalle copie presenti sul disco ma apparentemente inutilizzate. La verifica definitiva richiede comunque di controllare quale versione PHP risponda alle richieste dei singoli siti, perché sullo stesso server possono convivere più runtime differenti.
Un’installazione potrebbe utilizzare PHP 8.4 da riga di comando, PHP 8.2 attraverso un pool FPM e un ulteriore runtime PHP gestito dal pannello di hosting. Per ottenere un risultato affidabile bisogna quindi associare ciascuna applicazione al processo e all’eseguibile realmente utilizzati per elaborare le richieste HTTP.
Individuare PHP su Windows, anche quando non compare tra i programmi installati
Negli ambienti Windows la ricerca può partire da PowerShell, cercando ricorsivamente i file php.exe e php-cgi.exe nelle directory che ospitano applicazioni e servizi.
Un comando utile, da eseguire in una sessione amministrativa, è il seguente:
Get-ChildItem -Path 'C:\Program Files','C:\Program Files (x86)','C:\inetpub' -Include php.exe,php-cgi.exe -File -Recurse -ErrorAction SilentlyContinue
La ricerca può richiedere tempo e non dovrebbe limitarsi alle cartelle indicate nel comando che vi abbiamo presentato: applicazioni portabili, stack Web indipendenti e software installati su altri volumi potrebbero conservare i propri interpreti in percorsi differenti.
Occorre poi verificare le configurazioni di IIS, in particolare le associazioni FastCGI e gli handler che indirizzano le richieste .php verso uno specifico eseguibile.
Un ulteriore aiuto arriva dai sistemi EDR, cioè dalle soluzioni di rilevamento e risposta sugli endpoint: se raccolgono informazioni sui file eseguibili e sui processi, possono facilitare una ricerca centralizzata su centinaia o migliaia di macchine.
Inventario dei container: perché controllare soltanto l’host non basta
Una categoria particolarmente insidiosa è rappresentata dai container: su un sistema che usa Docker può non esistere alcuna installazione PHP visibile tramite il gestore dei pacchetti dell’host, mentre diversi container possono eseguire interpreti differenti.
La ricognizione deve quindi comprendere le immagini utilizzate, i container attivi e le rispettive dipendenze: il comando seguente offre un primo elenco delle immagini associate ai container in esecuzione. Le versioni PHP devono poi essere verificate dentro le immagini o attraverso i relativi metadati e manifest:
docker ps --format '{{.Names}} {{.Image}}'
La presenza di un tag come php:8.5 non basta per stabilire se la correzione sia presente. I tag possono indicare una famiglia di versioni anziché una build specifica e, soprattutto, un’immagine già scaricata potrebbe essere precedente alla pubblicazione della patch.
Per le applicazioni sviluppate internamente è opportuno aggiornare l’immagine di base, ricostruire il container e distribuire la nuova versione.
Come verificare se una versione PHP è davvero vulnerabile
Confrontare il numero di versione con quelli pubblicati dal team PHP costituisce il primo passaggio, ma non sempre basta.
Le distribuzioni Linux con supporto a lungo termine possono applicare le correzioni di sicurezza alle versioni precedenti del software, mantenendo invariato il numero della versione principale: è il meccanismo noto come backport delle patch.
Per esempio, un pacchetto che continua a identificarsi come PHP 8.2 potrebbe contenere una correzione fornita dal distributore, pur senza riportare esattamente il numero 8.2.35. La verifica deve quindi considerare anche la release del pacchetto, gli advisory del vendor e il changelog.
Un controllo basato esclusivamente sulla stringa restituita da php -v rischia di classificare erroneamente un sistema già messo in sicurezza. Viceversa, la presenza di un numero apparentemente recente non assicura che tutti i componenti siano stati aggiornati: potrebbero esserci processi ancora attivi che utilizzano la precedente libreria o un altro interprete non ancora corretto.
Il team PHP ha confermato che le versioni 8.1 e precedenti non ricevono più aggiornamenti ordinari dal progetto. Considerata l’eccezionale gravità dell’incidente, gli sviluppatori hanno comunque reso disponibili indicazioni e correzioni utilizzabili anche per alcune vecchie release, comprese le serie 7.4, 8.0 e 8.1, per chi mantiene compilazioni personalizzate.