EresusSecurity
Araştırmalara Dön
Zafiyet Analizi

PHP2Shell: PHP Çekirdeğinde Kritik RCE (CVE-2026-109618, CVE-2026-109619)

Yiğit İbrahim SağlamOfansif Güvenlik Uzmanı
21 Ekim 2026
20 dk okuma
Danışma AnaliziWeb AltyapısıKaynak: PHP güvenlik duyuruları GHSA-w8hw-w9fx-j79w ve GHSA-6wmf-4rv5-p3rpKaynak tarihi: 2026-10-21

Kısa cevap: CVE-2026-109618 ve CVE-2026-109619, WordPress, Laravel, Drupal veya başka bir uygulamada değil, doğrudan PHP çalışma zamanında bulunan bellek güvenliği hatalarıdır. Hazırlanmış HTTP istekleriyle tetiklenebilir; Apache mod_php üzerinde uygulama kodu çalışmadan önce devreye girer ve web worker hesabının yetkileriyle uzaktan kod çalıştırmaya kadar gidebilir. Yamalı sürümler PHP 8.5.12, 8.4.27, 8.3.36 ve 8.2.35'tir. Tek tam çözüm PHP'yi güncellemektir; her yapılandırma önlemi belirli bir saldırı yolunu kapatır, hata sınıfını ortadan kaldırmaz.

Başlık Ayrıntı
Tanımlayıcılar CVE-2026-109618 (OOM bozulması), CVE-2026-109619 (bayat global durum)
Duyurular GHSA-w8hw-w9fx-j79w, GHSA-6wmf-4rv5-p3rp
Önem derecesi 9.2, CVSS v4.0 — AV:N/AC:H/AT:P/PR:N/UI:N/VC:H/VI:H/VA:H
Yamalı sürümler 8.5.12, 8.4.27, 8.3.36, 8.2.35
Etkilenen dallar 8.2–8.5'te yamalı sürümden önceki tüm sürümler; Wiz ve Google Cloud hatanın PHP 5.4'e kadar uzandığını belirtiyor
Kimlik doğrulama Doğrulanan saldırı yollarında gerekmiyor
En riskli SAPI Apache mod_php
Yama tarihi 21 Ekim 2026

"PHP2Shell" tam olarak neyi ifade ediyor?

PHP2Shell, bellek güvenliği hatalarından oluşan bir kümenin kamuya açık adıdır. Cloudflare'in yazısı Wiz Research, Calif.io, OpenAI ve Quarkslab'ı anıyor; GHSA kayıtları bireysel araştırmacıları listeler ve Calif ile Quarkslab'ı adıyla anmaz. İki CVE atandı, ancak asıl sorun tek bir mimari kalıptır: PHP, bir isteği istisnai bir yolla iptal ederken istek durumu ya kısmen başlatılmış ya da worker'a ait global alanda yayımlanmış olabilir. Ardından gelen temizlik işlemi veya sonraki istek, saldırganın etkileyebildiği belleği geçerli veri gibi işler.

İki CVE de aynı kök neden ailesine aittir ve yama tek bir ayrıştırıcı hatasını değil, istek yaşam döngüsünü düzeltir. Wiz, iki tanımlayıcı altında dört gösterilmiş ilkel sayıyor: upload-progress unserializer use-after-free, uzaktan süreç belleği ifşası, fatal-error backtrace use-after-free ve OPcache tip karışıklığı. Ek varyantların da bulunması muhtemel. Bu, savunma tarafı için kritik bir sonuç doğurur: tek bir istek imzasını aramak, yama uygulamanın yerini tutmaz.

Hata uygulamaya özgü değildir. Wiz, güncel wordpress, drupal ve joomla konteyner imajlarında kimlik doğrulamasız kod çalıştırmayı gösterdi; ancak yalnızca yanıt döndüren bir "Hello World" PHP betiğinin de aynı motor seviyesindeki yolu açtığını belirtti. CMS'iniz, framework'ünüz veya WAF kural setiniz hatayı ortadan kaldırmaz.

CVE-2026-109618: bellek yetersizliği işlenirken bozulma

PHP, memory_limit sınırını longjmp() ile uygular. Bir bellek ayırma işlemi başarısız olduğunda PHP mevcut bağlamdan çıkar ve isteği iptal eder. Birkaç başlangıç yolunda istek belleği, tam olarak başlatılmadan önce erişilebilir durumdadır. Ayırma hatası bu pencerede gerçekleşirse PHP isteği geçersiz bir durumda bırakır; istek kapatma işlemi de okunmaması, dallanmaması veya serbest bırakılmaması gereken belleği işler.

Başarısız ayırmanın geçersiz yapıyla ilgili olması gerekmez. Bu nedenle bir istek, görünürdeki PHP sınırları içinde kalarak bile hatayı tetikleyebilir:

  • Kullanılabilir bir Content-Length bildirmeyen multipart istek, ilk post_max_size kontrolünü geçip çözülmüş gövde verisi sağlamaya devam edebilir.
  • Tek bir multipart parçası sınırsız sayıda başlık taşıyabilir. PHP'nin bellekteki gösterimi, kablo formatından çok daha fazla yer kaplar; post_max_size altındaki bir gövde memory_limit sınırını tüketebilir.
  • Boş dosya alanları max_file_uploads sayısına girmez, ancak normal dosya üstveri dizilerini yine oluşturur. İç içe alan adları, üretilen dizi işini katlar.

SAPI, hatanın kimlik doğrulamasından önce mi tetiklendiğini belirler:

SAPI Davranış Pratik risk
Apache mod_php İstek başlangıcı başarısız olsa bile istek kapatma prosedürünü koşulsuz çağırır Uygulamadan bağımsız, uygulama kodu çalışmadan kimlik doğrulamasız RCE; varsayılan sınırlarla doğrulandı
PHP-FPM Başlangıç başarısız olduğunda child süreci sonlandırır FPM için uygulama öncesi başlangıç yolu gösterilmedi; RCE uygulama düzeyindeki kod yollarıyla doğrulandı. Yine internetten erişilebilir ve yine acil
FrankenPHP mod_php gibi kapatmayı koşulsuz çağırır Uygulamadan bağımsız olması muhtemel; yalnızca kaynak analizi
LiteSpeed / LSAPI FPM modelini izler Uygulamaya özgü istismar muhtemel; doğrulanmadı
php-cgi PHP duyurusuna göre risk altında Özel olarak doğrulanmadı

Doğrulanan istismar ayrıntısı en önemli kısımdır: HTTP üzerinden, varsayılan girdi ve bellek ayarlarına sahip mod_php ve normal prefork yapılandırmasında istek uygulamaya hiç ulaşmaz. PHP, başarısız isteği temizlerken saldırganın komutunu çalıştırır. Birden fazla worker ve ilgisiz trafik, gereken deneme sayısını değiştirir; koşulun varlığını ortadan kaldırmaz.

Bunu "FPM güvenli" diye düzeltmeyin. PHP Foundation'ın sürüm notu, uzaktan kod çalıştırmanın PHP-FPM üzerinde de uygulama düzeyindeki kod yollarıyla doğrulandığını söylüyor; CVE-2026-109619 için use-after-free ve worker çökmesi doğrulanmış, RCE ise Apache mod_php üzerinde gerçek bir uygulamaya karşı gösterilmiş. Ayrım zincirin nerede başladığıyla ilgilidir, FPM'in güvenli olup olmadığıyla değil. mod_php daha kötüdür çünkü başarısız istek başlangıcı, herhangi bir uygulama kodu çalışmadan interpreter kapatmasını çalıştırabilir. FPM'e ise durumu yayımlayan bir uygulama işlemi ve sonraki istekte onu tüketen bir yol üzerinden erişilir.

CVE-2026-109618 ayrıca uygulamadan bağımsız bir bellek ifşası ilkeli sunar. Wiz, diğer isteklere ait parola, token ve anahtarları içerebilecek worker belleğinin kimlik doğrulamasız okunabildiğini gösterdi.

Yamanın içi: OOM işleyişi durum makinesine dönüşüyor

Yama tek satırlık bir sınır kontrolü değildir. "Avoid state corruption via bailout" başlıklı 3584a98bda0f2c0d367255b046798b0d3a221a19 commit'i 389 dosyayı değiştirir. ChangeLog kaydı açık: Fixed GHSA-w8hw-w9fx-j79w, GHSA-6wmf-4rv5-p3rp (Avoid state corruption via bailout). Yamanın şeklini anlamak operasyonel açıdan önemlidir; çünkü bazı uygulamaların bağlı olduğu davranışı değiştirir.

Yamadan önce memory_limit altında başarısız bir ayırma sonunda longjmp()'e ulaşıyordu. Bu, C yığınını o anda çalışan parser, allocator veya eklentinin içinden açar. İstek başlangıcı yalnızca yarı tamamlanmışsa, atlama başlatmayı atlayabilir ama kapatmanın sonradan geçerli sayacağı işaretçileri bırakabilir. Hata sınıfı, "istek var" ile "isteği yok etmek güvenli" arasındaki boşluktur.

Yamalı çalışma zamanı açık bir OOM yaşam döngüsü ekler:

ayırma isteği
  |
  +-- fallible ayırma? --> NULL döndür, longjmp yok
  |
  +-- fallible değil? --> soft limit aşıldı?
                         |-- evet: EG(delayed_oom) kaydet, vm_interrupt ayarla
                         |        güvenli executor sınırında işle
                         |
                         +-- hard limit (memory_limit'in 2 katı)?
                                  `_exit(137)`

8.5.12 ağacındaki temel parçalar:

  • Zend/zend_alloc.h, NONE, PENDING, HANDLING ve HANDLED durumlarına sahip zend_oom_state ile zend_oom_info { state, lineno, message, filename } tanımlar. Executor başına kayıt EG(delayed_oom)'dur. ZEND_HAS_OOM() bu durum üzerinde hızlı bir kontroldür.
  • Yeni fallible ayırma giriş noktaları (_femalloc, _fecalloc, _ferealloc, _ferealloc2, _safe_femalloc, _safe_ferealloc) çözülmek yerine NULL döndürür. OOM'a dayanması gereken çağrı noktaları bu API'lere çevrilir. Diff'in bu kadar büyük olmasının nedeni budur: yalnızca yeni bildirimler değil, ayırma yollarının dönüştürülmesidir.
  • Soft limit gecikmeli OOM'u kaydeder ve VM interrupt ister. zend_execute_scripts() çalıştırmadan sonra zend_handle_delayed_oom() çağırır; zend_call_function() durum NONE değilken kullanıcı koduna girmeyi reddeder. Hata, istek durumunun tutarlı olduğu bir sınırda üretilir.
  • Hard limit varsayılan olarak memory_limit'in %200'üdür ve fallible olmayan bir ayırma bu sınırı aşınca _exit(137) çağırır. Bu, normal bir hata yolu değil son çare containment'dır. Durumu bozmadan önce durmak istediği için kullanıcı shutdown fonksiyonlarını bilinçli olarak çalıştırmaz.
  • main/main.c, zend_activate()'ten hemen sonra ve sapi_activate()'ten önce php_basic_early_rinit() çağırır; böylece SAPI istek kurulumunu çalıştırmadan temel global'ler sıfırlanır. Gecikmeli OOM durumu istek kapatma sırasında temizlenir.
  • Zend/zend_execute_API.c, executor kapatması sırasında kullanıcı hata ve istisna işleyicilerini, işleyici dizilerini, record_errors, num_errors, errors, error_handling, geçerli istisnayı ve nesne deposunu (object_buckets = NULL, top = 1) sıfırlar. Bunlar tam olarak CVE-2026-109619'un kötüye kullandığı istekler arası işaretçilerdir.
  • Zend/zend_builtin_functions.c, debug_backtrace_get_args() fonksiyonunu bool döndürecek ve paketlenmiş, fallible dizi ayırması kullanacak şekilde değiştirir. Ayırma başarısız olursa false döner ve zend_fetch_debug_backtrace() geçersiz frame'de yürümek yerine durur. Bu yol, doğrulanmış mod_php RCE'sinin arkasındaki fatal-error backtrace tüketicisidir.
  • Zend/zend.c, OOM durumu HANDLING iken yakalanmamış istisna raporunu bastırır ve deaktivasyon sırasında zend_mm_oom_info_dtor çağırır. Amaç, OOM temizliği içinden kullanıcı işleyicilerini özyinelemeli çağırmamaktır.
  • ext/session/session.c, upload-progress işleyişini RINIT öncesi yolun kullanıcı kodu çalıştırmayacağı ve tam başlatılmamış sınıflara dokunmayacağı şekilde sertleştirir. Bu, özelliği yalnızca kapatmaktan daha güçlüdür.
  • SplFixedArray ve dizi yardımcıları (array_fill, array_pad) açık hata işleme ile fallible ayırmaya çevrilir. Bunlar erişilebilir OOM büyütme noktalarıydı.

Yeni PHPT kapsamı Zend/tests/oom_request_parsing.phpt içerir; php-cgi'yi memory_limit=8M, post_max_size=1G, max_input_vars=10000000, derin iç içe değişken adları ve sonunda & olmayan bir değerle çalıştırır. Hard-limit, soft-limit, call-function, debug-backtrace, SplFixedArray, array_fill ve array_pad OOM testleri ile ext/session/tests/rfc1867_no_user_code.phpt de vardır.

Operatörler için pratik değişiklikler:

  1. OOM artık tam ayırma noktasında iptal edilmek zorunda değildir. Fallible yollar NULL döndürür ve normal hata işleme üzerinden çözülür; ölümcül hata daha sonra güvenli bir noktada üretilir.
  2. Artık iki eşik vardır. memory_limit soft limittir; yaklaşık iki katı hard _exit(137) limitidir. Daha önce PHP fatal error ile ölen süreç şimdi 137 çıkış koduyla kaybolabilir. Bunu incelemeden kernel OOM killer sanmayın.
  3. Hard-limit yolunda kullanıcı shutdown fonksiyonları çalışmayabilir. Uygulamanız bellek tükenmesinden sonra register_shutdown_function() ile tampon boşaltma, kilit bırakma veya denetim kaydı yazmaya güveniyorsa bu davranışı açıkça test edin.
  4. Fallible ayırma eklenti davranışını değiştirir. Eski API'ye karşı derlenmiş üçüncü taraf eklenti hâlâ fallible olmayan ayırma çağırıp hard limite çarpabilir. Eklentileri yamalı başlıklara karşı yeniden derleyin ve test edin.
  5. Yama OOM'u bedava hale getirmez. Uygulama hâlâ bellek tüketebilir, hata döndürebilir ve istekleri düşürebilir. Yama durum bozulması penceresini kaldırır, kullanılabilirlik sorununu değil.

Bu nedenle "yamayı uygula ve 500'leri izle" yetersizdir. 137 çıkış kodunu, worker yeniden başlamalarını ve değişen shutdown davranışını izleyin; hata işlemenizin hâlâ düşündüğünüz şeyi yaptığını doğrulayın.

CVE-2026-109619: istekler arasında bayat worker durumu

İkinci CVE, istek sınırlarını aşan bir use-after-free hatasıdır. PHP; hata, oturum, nesne ve eklenti durumu gibi worker'a ait global alanlarda bir isteğe ait belleğe işaret eden referanslar tutar. İstek yığını serbest bırakılmadan önce bu durumun sıfırlanması gerekir. Bazı işlemler sonraki isteğin normal başlatılmasından önce çalışır ve bayat değeri önce okur.

İstismar için bir üretici ve bir tüketici gerekir:

  1. Erişilebilir bir işlem, isteğe ait durumu global olarak erişilebilir bir yere yazar.
  2. Durum sıfırlanmaz veya normal sıfırlamadan sonra bir tanılama mesajı onu yeniden doldurur.
  3. PHP istek yığınını serbest bırakır, ancak worker hâlâ referansı tutar.
  4. Aynı worker başka bir isteği işler.
  5. Normal başlatma değeri değiştirmeden önce bir işlem bayat değeri okur, serbest bırakır, üzerinde dallanır veya ona erişir.

Normal istek başlatmasından önce doğrulanan iki tüketici vardır:

  • INI tanılamaları. Yapılandırma uygulanırken ortaya çıkan bir uyarı, bildirim veya kullanımdan kaldırma mesajı bayat hata durumunu tüketebilir. Geçersiz ya da eski php.ini değerleri, Apache dizin ayarları ve frontend'den gelen PHP_VALUE/PHP_ADMIN_VALUE parametreleri adaydır. Tanılamanın görüntülenmesi veya günlüğe yazılması gerekmez. error_reporting, @, display_errors=0 ve log_errors=0 bu yola karşı koruma sağlamaz.
  • Oturum yükleme ilerlemesi. PHP'nin RFC1867 upload-progress işleyişi, olağan oturum başlatmasından önce oturum durumuna ulaşabilir. Uygulama hiç session_start() çağırmasa bile çalışır.

Doğrulanan ilkeller arasında fatal-error backtrace yolu (en güçlü senaryo ve doğrulanmış mod_php RCE'sinin temeli), oturum yükleme ilerlemesi yaşam döngüsü ve worker'lar arası OPcache tip karışıklığı bulunur. FPM yolu, mod_php'yi bu kadar tehlikeli yapan uygulama öncesi başlangıç yolu üzerinden değil, uygulama düzeyindeki kod yollarıyla gösterildi. Pratikte bu, FPM istismarının aynı worker üzerinde durumu yayımlayan, ölümcül hataya ulaşan ve sonraki istekte upload-progress tüketicisini bırakan erişilebilir bir işleme bağlı olduğu anlamına gelir.

Oturum bileşeni kesin bir uyarı hak ediyor. PHP'nin geçici önlem rehberi, Datadog'un aktardığına göre session.upload_progress.enabled ayarını listeliyor; Datadog ise bu tür topluluk önlemlerinin sizi tam olarak korumadığını belirtiyor. Ayarın yalnızca doğrulanmış oturum yollarını mı blokladığı PHP'nin birincil duyurusuna karşı bu makalede kontrol edilmedi. Bunu risk azaltma olarak görün, asla tam mitigasyon olarak görmeyin.

Yamanın sıfırlama mantığı, hata sınıfını herhangi bir tek istismardan daha iyi açıklar. Executor kapatması sırasında PHP artık kullanıcı hata işleyicisini ve istisna işleyicisini, işleyici dizilerini, kayıtlı hata listesini ve sayılarını, error_handling değerini, geçerli istisnayı ve nesne deposunu temizler. Bunlar istek belleğine işaret eden worker-global işaretçilerdir. Bunlardan biri sonraki isteğe sağ kalır ve başlatma onu değiştirmeden önce okunursa, sonraki istek serbest bırakılmış belleğe erişir. Yama sıfırlamayı açık hale getirir ve OOM işleyişini isteğin tutarlı biçimde yıkılabileceği bir noktaya taşır.

Savunma tarafının sık kaçırdığı bir sonuç var: uygulama günlüklerinde hiç görünmeyen bir istek, worker'ı yine de bozmuş olabilir. İsteğin framework logunda bulunmaması, güvenli olduğunun kanıtı değildir.

Etkilenen kurulumlar

Web isteği sunan her PHP kurulumu kapsamdadır: PHP-FPM, Apache mod_php, php-cgi, FrankenPHP ve LiteSpeed. PHP projesi mod_php dağıtımlarını en yüksek riskli grup olarak değerlendiriyor.

Dal Son savunmasız sürüm Yamalı sürüm Yukarı akış durumu
8.5 8.5.11 8.5.12 Destekleniyor
8.4 8.4.26 8.4.27 Destekleniyor
8.3 8.3.35 8.3.36 Güvenlik düzeltmeleri
8.2 8.2.34 8.2.35 31 Aralık 2026'ya kadar güvenlik düzeltmeleri
8.1 ve öncesi — Yukarı akış sürümü yok Yaşam sonu; 7.4, 8.0 ve 8.1 için minimal kaynak yamaları var
5.4–7.3 — Yok Yaşam sonu, yukarı akış düzeltmesi yok

PHP'nin kendi duyuruları desteklenen dallardaki etkilenen sürümleri listeler. Google Cloud ve Wiz, savunmasız kodun PHP 5.4'e kadar uzandığını belirtiyor; Google Cloud 5.4'ten 8.5.11'e kadar tüm sürümleri savunmasız sayıyor. CERT-EU'nun duyurusu PHP 5.4'ten söz etmiyor. Hâlâ 5.4–7.3 çalıştırıyorsanız, var olmayabilecek bir dağıtım veya tedarikçi yamasına güveniyorsunuz. Bu makineleri yamalanmamış ve açık kabul edin; ihlal iddiasını yalnızca sürüm numarasından değil, ana makine kanıtından çıkarın.

Sıklıkla gözden kaçan iki grup:

  • Gömülü PHP. İzleme cihazları, NAS ürün yazılımları, yazıcı sunucuları, VPN portalları ve OT yönetim arayüzleri, kilitli bir web arayüzünün arkasında eski bir PHP taşır. Bunlar hâlâ ağdan erişilebilen PHP SAPI'leridir.
  • Yönetilen ve sunucusuz PHP. App Engine standard, Cloud Run, Cloud Functions ve benzeri platformlar temel imajları otomatik yamalayabilir; ancak yalnızca otomatik güncelleme açıksa ve yalnızca desteklenen çalışma zamanları için. Özel konteyner, sabitlenmiş temel imaj veya yaşam sonu çalışma zamanı bu korumayı devralmaz.

Önce yamayı uygulayın, sonra gerçekten çalıştığını doğrulayın

Düzeltme 21 Ekim 2026 sürümlerinde. Dağıtımlar ve LTS tedarikçileri yamaları önceden aldı. Temel imaj etiketini, kilit dosyasını veya derleme bildirimini güncellemenin, trafiği karşılayan çalışma zamanını değiştirdiğini varsaymayın.

Doğrulama listesi:

  1. Derleme dosyasını değil, çalışan ikiliyi doğrulayın. Her konteynerde ve her sunucuda: php -v ve php -r 'echo PHP_VERSION, PHP_EOL;'.
  2. SAPI'yi doğrulayın. php -i | grep 'Server API' çıktısı Apache 2.0 Handler (mod_php), FPM/FastCGI, CGI/FastCGI ve LiteSpeed ayrımını verir.
  3. Worker'ları yeniden başlatın. FPM child süreçleri, Apache prefork worker'ları ve OPcache/preload edilmiş kod, yamalı ikiliden gelmelidir. Paket güncellemesi tek başına eski child süreçleri trafikte bırakabilir.
  4. Tüm filoyu döndürün. Bir havuzu kanarya olarak güncelleyin, doğrulayın, sonra geri kalanını boşaltıp değiştirin. Yalnızca genel web katmanını değil, otomatik ölçekleme gruplarını, cron ile çalışan PHP'yi, kuyruk tüketicilerini ve yönetim panellerini de kontrol edin.
  5. İmaj kimliğini etiketle değil, digest ile doğrulayın. Duyurudan önceki saatlerde bir tedarikçi imajı kullandıysanız, imajın yeniden derlenip derlenmediğini ve dağıtımınızın yeni digest'i gerçekten çekip çekmediğini kontrol edin.
  6. Geri dönüş yeteneğini koruyun. Yama, OOM işleyişini longjmp() yerine gecikmeli yumuşak OOM ve eşik aşılırsa _exit() kullanan sert OOM'a çevirir. Bellek tükenmesini yakalayan veya günlükleyen uygulamaları test edin.

Yaşam sonu dallar için PHP güvenlik ekibinin 7.4–8.1 minimal kaynak yamalarını yalnızca PHP'yi kendiniz derliyor ve sürdürebiliyorsanız kullanın. Aksi halde yükseltin. 5.4–7.3 için geriye dönük yama yok.

Geçici kontroller: faydalı, kısmi ve yanlış okunması kolay

PHP, hiçbir yapılandırma değişikliğinin tam azaltım olmadığını açıkça belirtiyor. Yama dağıtılırken maruziyeti azaltmak için şu sırayı kullanın.

1. Kontrol edilebilir OOM yolunu kaldırın (CVE-2026-109618)

memory_limit=-1 değerini yönetimsel olarak ayarlayın; örneğin FPM havuzunda veya Apache yapılandırmasında php_admin_value ile. Ardından hiçbir havuzun, dizinin, .htaccess dosyasının veya uygulama çağrısının sonlu bir sınırı geri getirmediğini doğrulayın ve tüm worker'ları yeniden başlatın. Bu, doğrulanmış istismarın kullandığı öngörülebilir istek başına hatayı kaldırır.

Tam değildir. PHP'nin yönlendirmesi birçok özetten daha dar: sınırı kaldırmak kontrol edilebilir OOM yolunu kapatır, ancak alttaki bir ayırma yine başarısız olabilir ve çalışma zamanının hata işleyişine ulaşabilir. mmap() veya başka bir alt seviye ayırma başarısız olursa, sonlu bir limit zayıf yola ulaşmanın tek yolu değildir. Gerçek bir bellek sınırıyla birlikte kullanın (4. madde) ve -1 değerini tek başına güvenlik kontrolü saymayın.

2. İstek girdisini küçültün ve sınırlayın

  • Uygulama yükleme gerektirmiyorsa post_max_size değerini 8M, gerekiyorsa 32M yapın; upload_max_filesize bunun altında kalsın.
  • max_file_uploads, max_input_vars ve max_input_nesting_level değerlerini düşürün.
  • Çözülmüş gövde boyutunu, multipart parça sayısını, parça başına başlık sayısını ve iç içe geçme derinliğini ters proxy veya yük dengeleyicide zorunlu kılın. Kullanılabilir Content-Length taşımayan istekleri de kapsayın.
  • Uygulama multipart form verisi kullanmıyorsa multipart/form-data isteklerini PHP'ye ulaşmadan engelleyin. mod_php için en yüksek değerli kontrollerden biridir.

3. CVE-2026-109619 zincirlerini kırın

  • PHP 8.5'te fatal_error_backtraces=0 değerini yönetimsel olarak ayarlayın. Bu, doğrulanmış RCE senaryosunun üreticisini kaldırır; her varyantı kapatmaz.
  • Yükleme ilerlemesine ihtiyacınız yoksa session.upload_progress.enabled=0 ayarlayın. Datadog, bu tür topluluk önlemlerinin sizi tam olarak korumadığını belirtiyor. Faydalı risk azaltmadır, tam mitigasyon değildir.
  • Performans elveriyorsa yüksek riskli havuzlarda pm.max_requests=1 düşünün. Bir worker'ın bayat durumu sonraki isteğe taşıma penceresini kısaltır.
  • Başlangıçta tanılama üreten eski veya geçersiz INI yönergelerini, Apache dizin ayarları dahil, kaldırın. İstek başına geçersiz kılmalar yerine başlangıç yapılandırmasını tercih edin.

4. Yanlış sınırları kullanmayın

memory_limit yerine RLIMIT_AS veya RLIMIT_DATA kullanmayın. Bu sınırlar limite ulaşıldığında mmap() çağrısını başarısız kılar; bu da tam olarak CVE-2026-109618'i tetikleyen yoldur. Konteyner veya cgroup memory.max daha iyi bir kullanılabilirlik sınırıdır; ancak her worker'ın kendi grubu yoksa cgroup'u öldürmek FPM master'ını ve tüm worker'ları götürebilir. Tek bir FPM child'ını öldürmek yalnızca o anki isteklerini etkiler ve master hızla yerine yenisini açar.

5. WAF'ı savunma derinliği olarak görün, çözüm olarak değil

Cloudflare, kamuya açıklamadan yaklaşık dokuz saat önce WAF korumalarını devreye aldı ve 21 Ekim 03:02 UTC'de ücretsiz ve ücretli planlarda varsayılan hale getirdi. Kurallar, yalnızca istek imzası yeterli olmadığı için tam işlem (full-transaction) tespiti kullanıyor. Bu değerli bir zaman kazandırır, düzeltme değildir: saldırganlar kurallara karşı yükleri çoktan mutasyona uğratıyordu ve savunmasız kod, WAF'ın modellemediği her yoldan hâlâ erişilebilir.

CVE-2026-109619'u azaltmayan yapılandırmalar: error_reporting, @ operatörü, display_errors=0 ve log_errors=0. Bayat duruma, PHP tanılamayı raporlayıp raporlamayacağına karar vermeden önce erişilir.

Tespit ve avcılık

İstismar uygulama kodu çalışmadan tamamlanabildiği için uygulama günlüklerinde anlamlı istek bağlamı bulunmayabilir. Tespiti çalışma zamanı ve uç nokta üzerine kurun.

Alarm üretmeye değer sinyaller:

  • HTTP 500 yanıtlarında ve üst akış 502/503 hatalarında artış; özellikle ardından worker değişimi veya OOMKilled olayları geliyorsa.
  • Allowed memory size of ... exhausted mesajları, PHP-FPM havuz tükenmesi ve açıklanamayan worker devri.
  • Kullanılabilir Content-Length taşımayan multipart istekler, çok yüksek parça başlığı sayısı, derin iç içe alan adları veya çok sayıda boş dosya alanı.
  • Set-Cookie yanıtlarında olağandışı büyük veya bozuk PHPSESSID değerleri. Wiz, bellek ifşası ilkelinin geri kazanılmış yığın verisini bu çereze URL-encode ederek yazdığını anlatıyor; bu makale bu davranışı yeniden üretmedi.
  • PHP2Shell kuralları için WAF olayları; özellikle aynı kaynaktan tekrarlanan varyantlarla izlenen engellenmiş istekler.
  • 500 dalgasının ardından web kullanıcısı tarafından açılan yeni dış bağlantılar, child süreçler veya dosya yazmaları.

Yalnızca istemci IP'sine göre değil, worker'a göre ilişkilendirin. Üretici ve tüketici isteklerinin aynı worker'a ulaşması gerekir; tek bir kaynak IP, izole bakıldığında zararsız görünen bir dizi üretmiş olabilir. Uçta istek kimliği varsa ama PHP'de yoksa, sırayı zamanlama ve worker yeniden başlatma olaylarıyla yeniden kurun.

Geçmiş günlükler güvenlik kanıtı değildir. Kullanımdan kaldırma mesajlarını dışlamış, başlangıç öncesi hataları yakalamamış ve yalnızca test edilen rotaları kapsamış olabilirler. Günlükleri yapılandırma incelemesi, sürüm envanteri ve sunucu düzeyi telemetriyle birlikte kullanın.

İstismardan şüpheleniyorsanız

Aksini kanıtlayana kadar web worker hesabıyla kod çalıştırıldığını varsayın. Worker genellikle uygulama koduna, yapılandırmaya, oturum deposuna, yükleme dizinlerine ve ortam değişkenlerine okuma erişimine sahiptir.

  1. Kanıtı yok etmeden sınırlayın. Havuzu boşaltın veya düğümü yük dengeleyiciden çıkarın. Platform izin veriyorsa süreç belleğini koruyun ve yeniden kurmadan önce disk anlık görüntüsü alın.
  2. Uç ve çalışma zamanı günlüklerini koruyun. WAF olayları, proxy günlükleri, FPM yavaş günlükleri, worker yeniden başlatma geçmişi ve konteyner olayları burada uygulama istek günlüklerinden daha önemlidir.
  3. Kalıcılığı avlayın. Yükleme ve oturum dizinlerinde beklenmeyen PHP dosyaları, .htaccess değişiklikleri, yeni cron işleri, authorized_keys, systemd birimleri, LD_PRELOAD ve olağandışı PHP eklentileri veya auto_prepend_file ayarlarını kontrol edin.
  4. Kimlik bilgisi erişimini kontrol edin. Env dosyaları, .env, veritabanı yapılandırmaları, bulut üstverisi erişimi, SSH anahtarları ve uygulama sırları worker'dan erişilebilir. Kapsamı anladıktan sonra, sınırlamadan sonra sırları döndürün.
  5. Yamalı imajdan yeniden kurun. İhlal edilmiş bir sunucudan webshell silmek düzeltme değildir. Yeniden derleyin, yeniden dağıtın ve yeni konteynerlerde çalışma zamanı sürümünü doğrulayın.
  6. Bildirin. Veri erişilebilir durumdaysa olayı potansiyel ihlal olarak ele alın ve hukuki/ sözleşmesel bildirim sürecinizi izleyin.

Yama tek başına geçmişte gerçekleşen erişimi geri almaz. Bellek ifşası ilkeli, kod çalıştırma olmadan da sırların sunucudan çıkmış olabileceği anlamına gelir.

9.2 puanı ve bağlamın önemi

CVSS v4.0 vektörü: AV:N/AC:H/AT:P/PR:N/UI:N/VC:H/VI:H/VA:H. Ağdan erişilebilir, ayrıcalık gerekmez, kullanıcı etkileşimi yok; gizlilik, bütünlük ve kullanılabilirlik etkisi yüksek. Karmaşıklık yüksek ve saldırı gereksinimleri mevcut; bu yüzden puan 10 değil 9.2.

Pratikte:

  • Varsayılan sınırlara sahip mod_php dağıtımları, güvenilir kimlik doğrulamasız istismara en yakın gruptur.
  • FPM dağıtımları, mod_php'yi bu kadar tehlikeli yapan uygulama öncesi yola otomatik olarak erişilebilir değildir; ancak RCE uygulama düzeyindeki kod yollarıyla doğrulandı ve CVE-2026-109619 uygun bir üretici/tüketici yoluna bağlıdır. mod_php acil durumdur; FPM de acildir.
  • İstismar taşınabilirliği PHP derlemesine, eklentilere, frontend davranışına ve ayırıcı düzenine bağlıdır. Daha fazla worker deneme sayısını artırır; koşulu ortadan kaldırmaz.
  • Bellek ifşası yolu uygulamadan bağımsızdır ve ölçekte tam RCE'den daha kolay silahlandırılabilir.

Kanıt olmadan bunu kendi kendine yayılan bir solucan olarak tanımlamayın. İnternete açık mod_php kurulumlarını ise acil durum olarak ele alın.

Açıklama zaman çizelgesi ve tedarik zinciri dersi

Tarih (2026) Olay
Ağustos (doğrulanmadı) GHSA-w8hw-w9fx-j79w, Wiz ve OpenAI bağlantılı araştırmacıları anıyor; Ağustos zamanlaması, Calif'in rolü ve aylar süren düzeltme ve varyant araması doğrulanmadı
20 Ekim CVE tanımlayıcıları dolaşıma girer ve PHP ön duyuru yayımlar
21 Ekim, sabah saatleri Doğrulanmamış bildirim: bir kavram kanıtı videosunun sızdığı ve tedarikçilerin yama öncesi istismar denemeleri bildirdiği belirtiliyor
21 Ekim, 03:02 UTC Cloudflare varsayılan WAF korumalarını etkinleştirir
21 Ekim, saat doğrulanmadı Doğrulanmamış bildirim: bir tedarikçinin, koordineli sürümden önce düzeltmeyi içeren konteyner imajları yayımladığı belirtiliyor
21 Ekim, 13:30 UTC CERT-EU 2026-018, düzeltmelerin 13:30 UTC'de "bugün" yayımlandığını belirtiyor
21 Ekim, ~14:00 UTC php.net sürüm arşivi 14:00 UTC'yi gösteriyor; bu, CERT-EU'nun 13:30 UTC ifadesiyle çelişiyor. 13:30–14:00 UTC penceresi çözülmemiş durumda
21 Ekim, öğleden sonra Kamuya açık yazılar ve PoC'ler yayılır; yoğun istismar denemeleri bildirilir

Savunma tarafı için iki ders:

  • Yama farkı bir istismar ilkelidir. Düzeltmeyi içeren imajlar duyurudan önce ortaya çıktığında, savunmacılar hâlâ beklerken saldırganlar değişikliği tersine mühendislikle inceleyebilir. İmaj digest'lerini ve kaynağını doğrulayın; erken yayımlanan bir tedarikçi etiketini körü körüne güvenli kabul etmeyin.
  • Maruziyet pencereniz duyuruda değil, sızıntıda başlar. Envanteri CVE kamuya açıldığında çıkarmaya başlarsanız, önemli saatleri çoktan kaybetmiş olursunuz.

24 saatlik eylem planı

Rol Eylem
Platform / SRE Her PHP çalışma zamanını ve SAPI'yi envanterleyin. Önce internete açık mod_php, sonra FPM ve FrankenPHP yamalayın. Worker'ları yeniden başlatın ve her konteynerde ikiliyi doğrulayın.
Uygulama güvenliği Multipart yükleme uç noktalarını, upload-progress kullanımını ve OOM'a ulaşabilen istek yollarını belirleyin. Uç sınırlar ekleyin. memory_limit davranışına bağlı kod yollarını kontrol edin.
SOC / olay müdahale WAF kurallarını etkinleştirin veya ayarlayın; worker devri ve 500 patlamalarında alarm kurun; uç günlüklerini koruyun; kimlik bilgisi döndürme ve webshell avı playbook'u hazırlayın.
Barındırma / yönetilen hizmet Hangi temel imajların yeniden derlendiğini, otomatik güncellemelerin açık olup olmadığını ve hangi müşterilerin yaşam sonu PHP çalıştırdığını doğrulayın. Net bir müşteri eylemi yayımlayın.
Yönetim Müşteriye dönük mod_php kurulumlarını sev-1 değişiklik penceresi olarak ele alın. Acil değişiklik kontrolünü onaylayın ve belirsizliği dürüstçe iletin: yamalı olan düzeltilmiştir, azaltılmış olan değildir.

Sık sorulan sorular

WordPress, Drupal veya framework'ümü güncellemek bunu düzeltir mi?

Hayır. Savunmasız kod PHP çalışma zamanındadır. Uygulamayı güncellemek, PHP'nin istek başlangıcını, OOM'u veya worker global durumunu nasıl işlediğini değiştirmez. PHP'nin kendisini güncellemelisiniz.

PHP-FPM güvenli mi?

Hayır. FPM, istek başlangıcı başarısız olduğunda child süreci sonlandırdığı için uygulama öncesi başlangıç yoluna daha az maruz kalır. Bu temiz bir sağlık raporu değildir: PHP Foundation, PHP-FPM üzerinde uygulama düzeyindeki kod yollarıyla RCE doğrulandığını söylüyor; CVE-2026-109619'un oturum ve fatal-error zincirleri de geçerlidir. Özellikle uygulama yükleme, oturum veya özel hata işleme yapıyorsa FPM'i aynı aciliyetle yamalayın.

memory_limit=-1 beni güvende yapar mı?

Doğrulanmış istismarın kullandığı kontrol edilebilir OOM tetikleyicisini kaldırır, ancak açıkça tam azaltım değildir. Alttaki ayırma hataları yine oluşabilir ve ayar yararlı bir kullanılabilirlik kontrolünü kaldırır. cgroup veya konteyner bellek sınırıyla birlikte kullanın ve -1 değerini güvenlik düzeltmesi saymayın.

CVE-2026-109619 için session upload progress'i kapatmak yeterli mi?

Hayır. Ayar bilinen bir oturum yolunu azaltabilir; Datadog bu tür önlemlerin tam koruma sağlamadığını belirtiyor. Diğer worker-global işaretçileri sıfırlamaz veya fatal-error backtrace yolunu kaldırmaz.

Yamalı worker'lar neden bazen 137 çıkış koduyla ölüyor?

Yama, memory_limit'in yaklaşık %200'ünde bir hard OOM limiti ekler; bu sınır aşılınca durum bozulmadan önce durmak için _exit(137) çağrılır. Bu, kernel OOM kill gibi görünebilir. Konteyner çalışma zamanını suçlamadan önce PHP bellek ayarlarını, tetikleyen isteği ve süreç çıkış geçmişini kontrol edin.

WAF bunu güvenilir biçimde engelleyebilir mi?

WAF zaman kazandırabilir ve Cloudflare'in tam işlem kuralları ciddi bir çabadır. Çalışma zamanındaki bellek güvenliği hatasını düzeltemez. Saldırganlar yamadan önce kurallara karşı yükleri mutasyona uğratıyordu ve yalnızca istek imzaları her üretici/tüketici dizisini modelleyemez.

Yaşam sonu bir PHP 5.x veya 7.x sunucusunu yamalayamıyorsam ne yapmalıyım?

Kimlik doğrulayan bir proxy arkasına izole edin, uçta multipart yüklemeleri engelleyin, genel internetten çıkarın ve değiştirme planı yapın. 5.4–7.3 için yukarı akış düzeltmesi yok. Uzun süredir internete açıksa, "hedef alınmayacak kadar gözden uzak" varsayımı yerine ihlal avı yapın.

Kaynaklar ve ileri okuma

AI Security Başlangıç Eğitimi

Prompt injection, RAG veri sızıntısı, MCP riskleri ve model dosyası güvenliği için pratik kontrol listesini e-posta ile isteyin.

Prompt injection ve koruma kuralı atlatma kontrolleri.
RAG veri sızıntısı ve izin sınırı incelemesi.
MCP kimlik, taşıma ve komut riski kontrolleri.

Spam yok. Yalnızca kaynağı ve ilgili güvenlik notlarını paylaşmak için kullanılır.

İlgili Araştırmalar

İlgili Hizmetler

Kapsam Tahmini

Kapsam görüşmesinden önce tahmini çalışma büyüklüğünü öğrenin.

Tahmini çalışma

5–7 gün

Kesin kapsam talebi