Guida pratica
Malware nascosto nei file PHP
Malware nascosto nei file PHP: metodo diagnostico, controlli in ordine e procedura sicura per intervenire senza modifiche casuali.

Risposta immediata: Un incidente va trattato come compromissione del sistema, non come singolo file. È essenziale determinare la finestra temporale, il vettore e la persistenza prima di dichiarare il sito pulito.
Il tema “Malware nascosto nei file PHP” va affrontato collegando configurazione, comportamento osservato e risultato atteso. Una procedura utile deve indicare anche limiti, rischi e controlli finali.
Questa guida adotta un percorso da risposta agli incidenti: contenere, preservare le prove, determinare il vettore, ripristinare e monitorare.
Contenimento iniziale
La rimozione del file visibile non equivale alla bonifica. Un incidente può lasciare account, cron, mu-plugin, drop-in, codice nel database, chiavi compromesse o una vulnerabilità ancora aperta. La sequenza corretta è contenimento, conservazione delle evidenze, bonifica, ripristino e verifica.
Il file system determina quali file WordPress può leggere, creare e aggiornare. Spazio, inode, proprietà, permessi e integrità dei file sono problemi distinti: un account può avere ancora gigabyte liberi ma non riuscire a creare nuovi file perché ha esaurito gli inode.
I log permettono di collegare il sintomo a un evento preciso. Il messaggio più utile è spesso il primo errore fatale o la prima risposta anomala nello stesso intervallo temporale, non l’ultima riga prodotta dopo una cascata di errori secondari.
Un incidente va trattato come compromissione del sistema, non come singolo file. È essenziale determinare la finestra temporale, il vettore e la persistenza prima di dichiarare il sito pulito.
Il test migliore cambia una sola variabile, produce un’evidenza leggibile e può essere annullato. Se non è possibile indicare cosa dimostrerebbe il successo o il fallimento del test, l’intervento è ancora troppo generico.
Raccolta e conservazione delle evidenze
Prima di modificare file, database o configurazioni, crea una fotografia minima della situazione. Questo permette di distinguere la causa dalla conseguenza e impedisce che una correzione apparente cancelli informazioni utili.
- vulnerabilità del componente
- timestamp e dimensione dei file
- output dei checksum
- uso disco e inode
- ownership e permessi
- prima riga fatale
- request URI e codice HTTP
- URL e percorso esatto in cui si manifesta “Malware nascosto nei file PHP”
- data e ora del primo episodio e dell’ultima modifica nota
- versioni di WordPress, PHP, tema e componenti coinvolti
Quando il sito gestisce ordini, moduli o dati aggiornati di frequente, annota anche l’ultimo record valido e stabilisci una finestra in cui evitare nuove modifiche. In questo modo il rollback non introduce una perdita di dati silenziosa.
Analisi del vettore e della persistenza
Procedi dal controllo meno invasivo a quello più profondo. La tabella non è una lista da eseguire meccanicamente: ogni riga deve confermare o escludere un livello del sistema.
| Passo | Controllo | Evidenza | Interpretazione |
|---|---|---|---|
| 1 | annotare URL, ruolo utente, browser, orario e risultato atteso | vulnerabilità del componente | Un errore nello stesso timestamp è più significativo di avvisi generici precedenti. |
| 2 | eseguire una sola modifica alla volta e registrare il risultato | timestamp e dimensione dei file | Confronta sempre il risultato con un caso funzionante dello stesso sito. |
| 3 | conservare un rollback verificato prima di operazioni su produzione | output dei checksum | Se il risultato cambia, il livello appena isolato partecipa direttamente al problema. |
| 4 | limitare modifiche e accessi senza distruggere le prove | uso disco e inode | Se non cambia, conserva l’esito e passa al livello successivo senza aggiungere altre modifiche. |
| 5 | confrontare core, plugin e tema con copie affidabili | ownership e permessi | Un errore nello stesso timestamp è più significativo di avvisi generici precedenti. |
| 6 | verificare amministratori, sessioni, cron, mu-plugin e drop-in | prima riga fatale | Confronta sempre il risultato con un caso funzionante dello stesso sito. |
| 7 | cercare PHP inatteso in uploads e modifiche recenti | request URI e codice HTTP | Se il risultato cambia, il livello appena isolato partecipa direttamente al problema. |
| 8 | controllare access log, WAF e vettore di ingresso | richieste POST anomale | Se non cambia, conserva l’esito e passa al livello successivo senza aggiungere altre modifiche. |
Dopo ogni passo annota “confermato”, “escluso” oppure “non verificabile”. La terza risposta è importante: segnala che serve un accesso, un log o un ambiente di prova, non che la causa sia stata esclusa.
Comandi di sola lettura o a basso impatto
Esegui i comandi solo se hai accesso autorizzato, dalla document root corretta e dopo avere verificato il backup. Sostituisci i domini di esempio e non incollare credenziali nei ticket.
Verifica non distruttiva dei file core con WP-CLI
wp core verify-checksums
Bonifica e ripristino
Le evidenze acquistano valore quando sono correlate. Un singolo warning, una scansione pulita o un test riuscito non bastano da soli a spiegare l’intero flusso.
- Se vulnerabilità del componente coincide temporalmente con il sintomo, verifica il componente che lo ha prodotto prima di intervenire su livelli non collegati.
- Se timestamp e dimensione dei file coincide temporalmente con il sintomo, verifica il componente che lo ha prodotto prima di intervenire su livelli non collegati.
- Se output dei checksum coincide temporalmente con il sintomo, verifica il componente che lo ha prodotto prima di intervenire su livelli non collegati.
- Se uso disco e inode coincide temporalmente con il sintomo, verifica il componente che lo ha prodotto prima di intervenire su livelli non collegati.
- Se ownership e permessi coincide temporalmente con il sintomo, verifica il componente che lo ha prodotto prima di intervenire su livelli non collegati.
- Se il problema compare soltanto da utente anonimo, controlla cache, cookie e differenze di rendering.
- Se compare soltanto da amministratore, verifica nonce, capability, plugin amministrativi e cache privata.
- Se il comportamento cambia tra browser ma la risposta server è identica, concentra l’analisi su JavaScript, cookie e dati locali.
Esempio di diagnosi ragionata
Supponiamo che il problema compaia subito dopo un aggiornamento, ma soltanto sul frontend anonimo. Il log non mostra fatal error e l’HTML contiene ancora il componente. Questo insieme di indizi rende più probabile una cache o un asset incoerente rispetto a un database danneggiato. La prova corretta è bypassare i livelli di cache e controllare lo status dell’asset, non reinstallare WordPress.
Rotazione degli accessi
Applica l’intervento minimo che risolve la causa confermata. Ogni azione deve avere un criterio di rollback e non deve distruggere le informazioni raccolte.
1. Ripristinare i soli file core senza sovrascrivere wp-content e wp-config.PHP
Non aggiungere altre ottimizzazioni nello stesso passaggio: altrimenti non saprai quale variazione ha prodotto il risultato.
2. Correggere proprietà e permessi secondo il modello del server
Se il test fallisce, ripristina la condizione precedente e conserva l’esito nel registro dell’intervento.
3. Liberare inode eliminando soltanto cache, log o backup verificati come sacrificabili
Prima di procedere salva configurazione e valore precedente. Dopo la modifica ripeti il test che aveva riprodotto il problema.
4. Abilitare il logging senza mostrare errori ai visitatori
Non aggiungere altre ottimizzazioni nello stesso passaggio: altrimenti non saprai quale variazione ha prodotto il risultato.
5. Riprodurre il problema con una sequenza breve e annotata
Se il test fallisce, ripristina la condizione precedente e conserva l’esito nel registro dell’intervento.
6. Estrarre le righe immediatamente precedenti e successive all’evento
Prima di procedere salva configurazione e valore precedente. Dopo la modifica ripeti il test che aveva riprodotto il problema.
7. Disabilitare il debug visibile e applicare una rotazione ai log dopo la diagnosi
Non aggiungere altre ottimizzazioni nello stesso passaggio: altrimenti non saprai quale variazione ha prodotto il risultato.
Cosa non fare
- cancellare subito ogni prova
- ripristinare un backup potenzialmente già infetto
- modificare più componenti contemporaneamente
- cancellare file o dati prima di conservarne una copia
- considerare risolto il problema dopo un solo test
- lasciare debug o strumenti temporanei attivi in produzione
Verifica post-incidente
La scomparsa del messaggio non basta. Il controllo finale deve coprire il flusso principale, gli effetti collaterali e il comportamento dopo il ripristino di cache, firewall o automazioni temporaneamente disattivate.
- nessun file o utente sospetto ricompare
- log e scansioni restano puliti nel periodo di osservazione
- la funzionalità principale completa l’intero flusso senza errori
- i log non registrano nuove anomalie durante più prove
- la correzione funziona sia per utente autenticato sia anonimo quando pertinente
- cache e servizi esterni sono stati riattivati e verificati
Registra data, versione, modifica applicata e risultato. Per problemi intermittenti osserva il sito per un intervallo coerente con la frequenza del guasto; un test immediato può non intercettare cron, cache o webhook che lavorano in seguito.
Prevenzione e piano di risposta
La prevenzione utile non consiste nell’installare molti strumenti, ma nel ridurre variabili sconosciute e rendere disponibili dati affidabili quando qualcosa cambia.
- tenere i backup fuori dalla document root
- limitare cache e log senza rotazione
- conservare log per un periodo coerente
- non lasciare debug display attivo
- includere timestamp e ID nelle integrazioni personalizzate
- mantenere un inventario di versioni, accessi e integrazioni
- prevedere un controllo dopo gli aggiornamenti
Per i siti con vendite, lead o integrazioni esterne, aggiungi alla manutenzione un test funzionale reale ma controllato: apertura modulo, ricezione email, ordine di prova, webhook, login e verifica della sitemap secondo il tipo di sito.
Riferimenti ufficiali
I percorsi e i comandi possono cambiare tra versioni. Prima di intervenire, confronta la procedura con la documentazione della versione installata e conserva un rollback verificato.
Domande frequenti
Un limite inode può interrompere un aggiornamento?
Sì. L’operazione può rimuovere file vecchi e non riuscire a creare quelli nuovi.
Quali permessi sono corretti?
Dipende dal modello del server; in genere file e cartelle devono essere scrivibili solo dai soggetti necessari, non da chiunque.
Il debug.log contiene sempre la causa?
No. Può contenere sintomi secondari; va correlato con log del server e azione eseguita.
Posso lasciare WP_DEBUG attivo?
Il logging può essere temporaneamente attivo, ma la visualizzazione pubblica degli errori va evitata.
Quanto tempo serve per diagnosticare malware nascosto nei file PHP?
Non esiste un tempo affidabile senza conoscere accessi, frequenza del problema e qualità dei log. Una buona raccolta iniziale riduce i tentativi e consente di stimare il lavoro dopo i primi controlli.
È meglio intervenire direttamente sul sito online?
Solo per verifiche a basso impatto. Modifiche a plugin, database, pagamenti, sicurezza o infrastruttura dovrebbero essere provate in staging o accompagnate da backup e rollback verificati.