Aktuální situace: PHP2Shell. Dvě kritické zranitelnosti PHP (CVSS 9.2) umožňují spustit škodlivý kód bez přihlášení. Záplaty od 21. 10. 2026.Co nyní udělat →

Varovný signál: webový server spouští shell

Spustí-li proces PHP-FPM nebo webového serveru shell, je to jeden z nejsilnějších varovných signálů průniku. Jak zkontrolovat strom procesů, zařadit výjimky a vzorec trvale sledovat.

Stav 5 min čteníDetekce a forenzní analýza

Stručně: Pokud PHP-FPM, Apache nebo jiný proces webového serveru spustí shell jako sh nebo bash, je to jeden z nejsilnějších varovných signálů průniku přes web. Zkontrolujte strom procesů, příkazovou řádku a pracovní adresář shellu, než cokoli ukončíte. Jednotlivé krátké shelly mohou být legitimní; dlouho běžící shelly se síťovými nástroji téměř nikdy.

Proč tento vzorec tolik vypovídá

Webový server odpovídá na požadavky. PHP-FPM, tedy správce procesů, který pro webový server spouští skripty PHP, k tomu normálně žádné další programy nespouští. Shell pod webovým serverem znamená, že kód PHP záměrně zavolal program. Buď to aplikace dělá úmyslně, nebo někdo jiný vložil kód.

Pro PHP2Shell neexistují zveřejněné, potvrzené indikátory kompromitace (Indicators of Compromise), tedy žádný seznam pevných rozpoznávacích znaků. Detekce se opírá o chování. Podle zpráv, které máme k dispozici, patří procesy webového serveru nebo PHP-FPM, které spouštějí shell, k nejsilnějším obecným varovným signálům. To platí pro každou zranitelnost, přes kterou útočníci spouštějí kód na serveru. Přehled dalších příznaků podává článek Jsem už kompromitován?.

Proč je shell pro útočníka tak důležitý? Se zranitelností může zprvu zadávat jen jednotlivé příkazy přes proces PHP. Shell z toho dělá pohodlné pracoviště: může se rozhlédnout, stáhnout nástroje, číst přístupové údaje z konfiguračních souborů a trvale se zabydlet. Kdo shell rozpozná, často rozpozná útočníka právě ve chvíli, kdy přechází od prvního přístupu ke skutečnému záměru.

PHP-FPM spouští bash: číst strom procesů

Každý proces v Linuxu má rodičovský proces. Otázka zní, zda shell běží jako potomek procesu webového serveru. Následující příkazy jen čtou:

# Strom procesů s uživatelem, PID rodiče a časem spuštění
ps -eo user,pid,ppid,lstart,cmd --forest | grep -B2 -A4 -E "[p]hp-fpm|[a]pache2|[h]ttpd|[l]sphp"

# Shelly běžící pod typickými uživateli webového serveru
ps -eo user,pid,ppid,lstart,cmd | grep -E "^(www-data|apache|nginx) " | grep -E "[ /](ba|da)?sh( |$)"

# Strom od nejstaršího procesu PHP-FPM
pstree -alp "$(pgrep -o php-fpm)"

Našli-li jste podezřelý shell, poskytují položky pod /proc další vodítka, rovněž jen čtecí:

PID=12345   # PID podezřelého shellu
tr '\0' ' ' < /proc/$PID/cmdline; echo        # úplná příkazová řádka
ls -l /proc/$PID/cwd /proc/$PID/exe            # pracovní adresář a soubor programu
ls -l /proc/$PID/fd 2>/dev/null | grep socket  # otevřená síťová spojení

Názvy procesů v Debianu a Ubuntu zní často php8.3-fpm nebo podobně; vyhledávací vzory upravte. Pracovní adresáře v /tmp, /dev/shm nebo ve složkách uploadu jsou zřetelným znamením.

Legitimní výjimky a skutečné varovné znaky

Některé aplikace volají přes PHP programy. Přitom může krátce vzniknout shell, například když PHP předává poštu přes sendmail_path nebo aplikace zpracovává obrázky externím nástrojem. Takové shelly žijí jen vteřiny a volají vždy tentýž program. Tyto očekávané případy jednou čistě zdokumentujte; pak každá odchylka hned upoutá pozornost, místo aby zanikla v záplavě známých hlášení.

Pozorování Spíše neškodné, když Podezřelé, když
Krátký shell pod PHP-FPM spouští známý program aplikace cíl a účel jsou nejasné
Déle běžící shell nikdy běží minuty nebo hodiny
Síťové nástroje jako podřízený proces známý dotaz aplikace na aktualizaci nebo API následují stahování do dočasných adresářů
Pracovní adresář složka projektu aplikace /tmp, /dev/shm, složky uploadu
Čas odpovídá známé akci, např. odeslání pošty v noci, bez aktivity uživatelů, nahloučeně

Pokud nevíte, zda vaše aplikace volá programy, zeptejte se vývojáře nebo v kódu hledejte funkce jako exec, shell_exec, system, passthru, proc_open a popen. Nálezy ve vlastním kódu jsou normální, nálezy v neznámých souborech nikoli.

Sledovat trvale, ne jednou nahlédnout

Momentka pomocí ps zachytí jen shelly, které právě běží. Krátkodobé procesy proklouznou. Spolehlivější je spouštění programů uživatelem webového serveru trvale protokolovat. V Linuxu to zajišťuje auditní služba auditd s pravidlem pro spouštění programů uživatelem webového serveru. Vyhodnocuje se čtecím způsobem:

# Zobrazit protokolovaná spuštění programů pod klíčem pravidla (klíč jako příklad)
sudo ausearch -k web_exec --start today -i | grep -E "exe=|proctitle="

Jak pravidlo vypadá, závisí na distribuci a ID uživatele; nejprve je otestujte, protože na silně zatížených serverech vzniká mnoho záznamů.

Dvě doplnění činí sledování odolným. Za prvé by protokoly měly navíc směřovat do centrálního systému, protože útočník s právy root může lokální logy smazat. Za druhé je třeba upozornění: Spuštění programu uživatelem webového serveru, které není na krátkém seznamu očekávaných programů, by mělo vyvolat hlášení, nejen záznam v logu. Kdo už používá řešení pro detekci na koncových zařízeních nebo serverech, může stejné pravidlo zobrazit tam. Preventivně lze pomocí disable_functions zakázat, co aplikace nepotřebuje. Nezavírá to zranitelnost v interpretu, ale ztěžuje to další krok útočníka. Podrobnosti najdete v článku Správné použití disable_functions.

Co dělat, když najdete shell pod webovým serverem

  1. Zdokumentovat: Výstup ps, příkazovou řádku, pracovní adresář a otevřená spojení uložit do souboru mimo webový adresář.
  2. Neuklízet: Nemazat soubory ani neukončovat procesy, dokud nejsou stopy zajištěny.
  3. Izolovat: Server odpojit od sítě nebo přístup silně omezit.
  4. Hledat příčinu: Zkontrolovat logy, nové soubory a perzistenci, jako jsou cron úlohy, viz Hledání podezřelých procesů na serverech s Linuxem.
  5. Změnit přístupy: Všechna hesla a klíče, které na serveru ležely, považujte za známé.

Běží-li aplikace v kontejnerech, platí stejný princip v malém. Shell v kontejneru PHP je stejně podezřelý jako na klasickém serveru a image kontejnerů ho často obsahují jen proto, že ho přináší základní image. Před restartem kontejneru zajistěte jeho stav, protože s kontejnerem mizí i stopy v prchavém souborovém systému.

Zkontrolujte také okolí. Útočník se shellem na webovém serveru se z něj často pokouší dostat k jiným systémům, například k databázi, úložišti záloh nebo interním administračním rozhraním. Přístupové údaje v konfiguračních souborech aplikace mu to usnadňují.

Jednejte ihned

Dlouho běžící shell pod PHP-FPM na serveru se zákaznickými daty je bezpečnostní incident. Zacházejte s ním tak: zajistit, izolovat, strukturovaně zpracovat, nechat prověřit oznamovací povinnosti.

Jak konkrétně pomáhá PHP SOS?

  • Zařadit nález: Kontrolujeme strom procesů, příkazové řádky a spojení a oddělujeme chování aplikace od stop průniku.
  • Zajistit stopy: Stav systému zajistíme dohledatelně, než se cokoli změní.
  • Zpracovat incident: V rámci Incident Response vedeme od zadržení po zdokumentované uzavření.
  • Trvale zabezpečit: Zavádíme protokolování spouštění programů a omezujeme funkce PHP na nezbytné. Jak PHP-FPM uvnitř pracuje, vysvětluje PHP-FPM vysvětleno.

Časté dotazy

Je každý shell pod PHP-FPM útokem?

Ne každý. Některé aplikace záměrně volají přes PHP programy, například pro úpravu obrázků nebo odesílání pošty, a přitom může krátce vzniknout shell. Podezřelé je to, když shell běží delší dobu, spouští síťové nástroje nebo pracuje v netypických adresářích.

Mám podezřelý proces okamžitě ukončit?

Nejprve dokumentovat, pak jednat. Zachyťte data procesu, příkazovou řádku, pracovní adresář a síťová spojení. Poté server izolujte. Ukvapené ukončení ničí stopy a nezabrání útočníkovi, aby se vrátil.

Existují pro PHP2Shell potvrzené rozpoznávací znaky?

Ne. Neexistují zveřejněné, potvrzené indikátory kompromitace. Shelly pod webovým serverem jsou obecným varovným signálem průniků přes webové aplikace, ne specifickým pro PHP2Shell.

Jak zabránit, aby PHP vůbec spouštělo shelly?

Pomocí disable_functions lze zakázat funkce jako exec, shell_exec, system a proc_open, pokud je aplikace nepotřebuje. Nezavírá to zranitelnost v interpretu PHP, ale ztěžuje to zneužití.

Zdroje

Okamžitý kontakt

Každá hodina se počítá. Napište nám hned.

Stručně popište systém, verzi PHP a pozorování. Ozveme se, vyjasníme situaci a budeme pracovat na dálku, dokud nebude incident uzavřen a zdokumentován.

Okamžitá pomoc