Yönetici özeti
- Araç ve altyapısı: 18 Eylül – 2 Kasım 2026 arasında, koruduğumuz web uygulamalarını 43 farklı IP adresinden tarayan bir aracı (bu yazıda Araç A) izledik. Adreslerin hepsi Google Cloud'da; 42'si Belçika bölgesinde (europe-west1).
- Liste: Araç 8 Ekim'den bu yana her taramada 112 yollu sabit bir çekirdek liste kullanıyor ve buna çoğu taramada değişen küçük bir "tema" ekliyor.
- Çekirdekte
.env, Git ve AWS dosyalarının yanında.claude/settings.json,.env.anthropicve.env.openaivar. - Temalarla birlikte yapay zekâ asistanı, LLM platformu ve MCP yollarının sayısı 32'ye çıktı (AI21, Mistral gibi başka model sağlayıcıları ve ses/görüntü API'leriyle birlikte 44). Aralarında
.claude/credentials.json,.openai/credentialsgibi kimlik bilgisi dosyaları ve.cursor/mcp.json,.vscode/mcp.jsongibi MCP yapılandırmaları var.
- Çekirdekte
- Ortak bir merkezden yönetiliyor gibi: Aynı tema aynı günlerde farklı IP'lerden geldi (30 Ekim – 2 Kasım arasında 7 IP'den birebir aynı küme); aynı IP ise neredeyse her gelişinde başka bir tema getirdi (birden fazla gelen 22 IP'nin 21'i).
- Hız ve geri dönüş: Taramaların yarısı 2,5 saniyeden kısa sürüyor; bu hızda IP engeli o taramayı durduramaz. Ancak adresler geri dönüyor: 83 oturumun 41'i daha önce görülmüş bir IP'den geldi.
- Bizi koruyanlar: İsteklerin %69'unu durduran kenardaki kurallar ve web kökünde bulunacak bir şey olmaması. İncelediğimiz taramaların hiçbirinde veri sızmadı.
- En önemli ders: SIEM'imiz bu aracın ekim–kasımdaki 42 adresinden yalnızca 11'ini gördü. Kalanını WAF kayıtlarında çekirdek listeyi arayarak bulduk.
- Tek araç bu değil: Aynı haftalarda beş farklı tarayıcı kimliğiyle çalışan ikinci bir araç ve ağustosta 17 yapay zekâ yolunu deneyen üçüncü bir araç gördük. 30 günde 205 farklı IP sistemlerimizde gizli dosya aradı; bunların %54'ü Google Cloud'dandı.
Arka plan
Açıkta kalan dosyalardan anahtar toplamak ve bu anahtarları paraya çevirmek yeni değil:
- Unit 42 (2024): 110.000 alan adındaki açık
.envdosyalarından toplanan anahtarlarla AWS ortamlarına girilip S3 verilerinin silindiği ve fidye notu bırakıldığı bir gasp operasyonunu belgeledi. - Sysdig, EMERALDWHALE (2024): Açık
.git/configdosyalarını tarayıp 15.000'i aşkın bulut kimlik bilgisi toplayan bir operasyonu raporladı. - Sysdig, "LLMjacking" (2024): Çalınan bulut anahtarlarıyla yapay zekâ modellerine erişildiğini ve faturanın hesap sahibine kaldığını gösterdi.
Gözlemlerimiz bu eğilimin sürdüğünü gösteriyor. En az iki ayrı tarama aracı, bulut anahtarlarının yanında yapay zekâ araçlarının yapılandırma ve kimlik bilgisi dosyalarını da arıyor.
Araç A'yı nasıl bulduk
İlk ipucu SIEM'den geldi. Wazuh, "kısa sürede çok sayıda 4xx" kuralıyla eylül sonundan itibaren aynı türden taramalar için alarm üretiyordu. Bu alarmların arkasında 112 yollu sabit bir liste olduğunu fark edince, aynı listeyi WAF kayıtlarımızda aradık. Ekim–kasımda alarm üreten adres sayısı 11'di; aynı listeyi deneyen adres sayısı ise 42 çıktı.
| Dönem | IP | Kaynak |
|---|---|---|
| 18 Eylül | 2 | Alarm satırları ve o günün trafik inceleme notu: 35.205.254[.]119 Araç A'nın kesik tarayıcı kimliğiyle geldi; 34.38.113[.]44 .claude, .anthropic ve gcloud dosyalarını aradı |
| 24 Eylül | 1 | 34.62.82[.]165: çok daha büyük bir liste (inceleme notuna göre 283 istek; 111 farklı yolda 4xx; yapay zekâ yolları dahil) |
| 26 Eylül | 1 | 34.38.113[.]44: ekim çekirdeğine çok yakın bir liste (4xx alan 30 yolun 24'ü çekirdekte) |
| 5 Ekim – 2 Kasım | 42 | WAF kayıtları: 20 günde 83 oturum, 100 hedef taraması |
18 Eylül satırındaki iki adres ekimde de çekirdek listeyle taradı: 35.205.254[.]119 12 ve 19 Ekim'de, 34.38.113[.]44 10 ve 20 Ekim'de. 34.62.82[.]165'i ise yalnızca 24 Eylül'de gördük.
Araç A nasıl çalışıyor
Sabit çekirdek, dönen tema.
- 8 Ekim – 2 Kasım arasındaki 93 hedef taramasının hepsinde çekirdeğin ana sayfa dışındaki 111 yolu eksiksiz vardı.
- Çoğu taramaya ayrıca 0–10 yollu, çoğunlukla birbiriyle ilgili bir küme eklendi; en sık 6 yol.
- 23 Ekim öğleden sonrasına kadar tema içeren 66 taramada 51 farklı küme gördük. Bir oturumun ikinci hedefine giden aynı küme dışında, yalnızca 3 küme başka bir oturumda yeniden görüldü.
- 23 Ekim öğleden sonra durum değişti: o gün ilk kez gelen
/.cursor/mcp.jsonve/.netrc, sonraki 24 taramanın 24'ünde de vardı. Deneme olarak eklenen yollar kalıcı listeye geçmiş görünüyor.
| İlk görüldüğü gün | Tema | Örnek yollar |
|---|---|---|
| 5 Ekim | sosyal medya ve muhasebe API anahtarları, Vault, CI iş akışları | /.env.facebook, /xero.json, /.vault.json, /.github/workflows/production.yml |
| 8 Ekim | yapay zekâ ve medya API'leri, mobil uygulama klasörleri | /.env.claude, /.env.elevenlabs, /.env.stability, /flutter/.env |
| 9 Ekim | izleme ve e-posta hizmetleri | /.env.betterstack, /.env.uptimerobot, /.env.brevo |
| 10 Ekim | kendi sunucusunda barındırılan CI, barındırma platformları | /.drone.yaml, /.woodpecker.yaml, /.netlify/.env, /.vercel/.env |
| 11 Ekim | yapay zekâ kimlik bilgileri; ödeme, kimlik doğrulama, e-posta pazarlama | /.claude/credentials.json, /.openai/credentials, /openai.key, /.env.mercadopago, /.env.frontegg |
| 12 Ekim | yapay zekâ ve gözlemlenebilirlik platformları | /.env.ai21, /.env.writer, /grafana.json, /dynatrace.json |
| 13 Ekim | yapay zekâ asistanları ve LLM platformları, Azure | /.claude/auth.json, /.anthropic/credentials.json, /.gemini/settings.json, /langsmith.json, /portkey.json, /.azure/credentials.json |
| 16 Ekim | API anahtar dosyaları, GitHub / GitLab token'ları | /.api-keys, /.github/token, /.gitlab/credentials |
| 17 Ekim | Elasticsearch / Solr, iş uygulamaları ve içerik yönetim sistemleri | /_cat/indices, /odoo.conf, /owncloud/config/config.php, /strapi/.env |
| 18 Ekim | bulut geliştirme ortamları, Matrix, Zabbix | /.config/gitpod/credentials, /.coder/credentials, /matrix/homeserver.yaml, /zabbix/conf/zabbix.conf.php |
| 19 Ekim | barındırma ve finans teknolojisi platformları | /.env.kinsta, /.env.qovery, /.env.lithic |
| 22 Ekim | MCP, gcloud | /.continue/config.json, /mcp.json, /.config/gcloud/application_default_credentials.json |
| 23 Ekim | MCP ve kimlik dosyaları | /.cursor/mcp.json, /.vscode/mcp.json, /.netrc, /.composer/auth.json |
| 30 Ekim | sunucu yönetim uçları | /actuator/env, /server-info, /.htaccess |
Temalar hedefin kullandığı teknolojiyle ilgili görünmüyor. Örneğin ödeme sağlayıcısı teması ödeme almayan bir uygulamada, LLM platformu teması yapay zekâ kullanmayan bir uygulamada denendi.
Tema IP'ye değil, göreve bağlı.
- Birden fazla kez gelen 22 IP'nin 21'i farklı gelişlerinde farklı temalar getirdi. Örneğin 34.53.184[.]30, 10 hedef taramasında 8 farklı tema denedi.
- Aynı tema ise farklı IP'lerden geldi:
- 23–28 Ekim arasında 6 IP birebir aynı üç yollu ek kümeyle geldi (
/.cursor/mcp.json,/.netrc,/sentry.properties); 4 IP daha bu üçlüye birkaç yol ekledi. - 30 Ekim – 2 Kasım arasında 7 IP birebir aynı ek kümeyle geldi.
- 23–28 Ekim arasında 6 IP birebir aynı üç yollu ek kümeyle geldi (
Bu örüntü, işçi makinelerin ortak bir merkezden görev ya da liste güncellemesi aldığını düşündürüyor.
Hız.
- Bir IP'nin bir saat içindeki taraması (bu yazıda "oturum"; 83 oturum) ortanca 2,5 saniye sürdü.
- Oturumların 29'u 2 saniyenin, 63'ü 10 saniyenin altında kaldı. En uzunu 41 saniye.
- Hedef başına 111–128 yol denendi.
Kimlik.
- İsteklerin %97'si sonu kesik şu tarayıcı kimliğiyle (User-Agent) ve
Accept-Encoding: gzip, deflatebaşlığıyla geldi:Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 - Gerçek bir Chrome bu dizgiyi
(KHTML, like Gecko) Chrome/… Safari/…ile bitirir. - Kalan istekler tam bir tarayıcı kimliği kullandı; en sık iki yıllık Chrome 128. Bunlar ana sayfa ve sayfa kaynaklarıydı.
- Aynı kesik kimliği ekim–kasımda Google Cloud dışından gelen 53 adres de kullandı; bunların hiçbiri çekirdeğin üçte ikisinden fazlasını denemedi. Kimlik tek başına yeterli bir imza değil.
Önce sayfayı okuyor. 100 hedef taramasının 83'ünde ana sayfa, 22'sinde sayfanın yüklediği JavaScript paketleri de istendi. Araç muhtemelen bu dosyaların içinde unutulmuş anahtar arıyor.
Hedefler. Alan adlarının hem www'li hem www'siz hâline, yük dengeleyicilerin ham IP adreslerine de geldi; toplam 13 farklı ad ve adres. Hedeflerin nasıl seçildiğini bilmiyoruz.
Ne arıyor
112 yollu çekirdeğin dağılımı:
| Kategori | Yol | Örnekler |
|---|---|---|
.env dosyaları |
49 | /.env, /.env.production, /api/.env, /laravel/.env |
| Uygulama yapılandırması | 22 | /appsettings.Production.json, /secrets.json, /config.php, /phpinfo.php |
| Bulut kimlik bilgileri | 12 | /.aws/credentials, /.boto, /.s3cfg, /aws-exports.js |
| Git | 8 | /.git/config, /.git-credentials, /.github/workflows/deploy.yml |
| Docker ve dağıtım | 7 | /docker-compose.yml, /.docker/config.json, /Dockerfile |
| Yedek ve veritabanı | 6 | /database.sql, /.env.bak, /wp-config.php.bak |
| Yapay zekâ araçları | 4 | /.claude/settings.json, /.claude/settings.local.json, /.env.anthropic, /.env.openai |
| Diğer | 4 | ana sayfa, /phpinfo, /_profiler/phpinfo, /wp-content/debug.log |
Araç A'nın 5 Ekim – 2 Kasım arasında denediği yolların listesi yazının ekinde: sitelerimize özgü 21 yol çıkarıldıktan sonra 411 yol; bunların 32'si yapay zekâ asistanlarına, LLM platformlarına ve MCP'ye ait (diğer yapay zekâ API'leriyle birlikte 44).
Neden yapay zekâ dosyaları
Kod asistanları ve LLM platformları ayarlarını, bazen de anahtarlarını, proje klasöründeki düz metin dosyalarda tutar:
.claude/settings.json,.gemini/settings.json: Asistanın ayarları, izin verilen komutlar, bazen ortam değişkenleri..claude/credentials.json,.anthropic/credentials.json,.openai/credentials,openai.key: Adlarından anlaşıldığı gibi doğrudan anahtar ya da oturum bilgisi için kullanılan dosyalar..cursor/mcp.json,.vscode/mcp.json,mcp.json,.continue/config.json: MCP sunucularının tanımları. Bu dosyalarda veritabanı, GitHub ya da bulut hesaplarına bağlanmak için kullanılan token'lar bulunabilir; tek bir dosya birkaç sisteme birden giden anahtarları taşıyabilir..env.anthropic,.env.openai,langsmith.json,portkey.json,helicone.json: Model sağlayıcılarının ve LLM gözlemlenebilirlik platformlarının anahtarları.
Bu dosyalar proje klasörüyle birlikte yanlışlıkla web köküne kopyalanırsa, tek bir GET isteği yapay zekâ hesabınızın anahtarını da (faturası size kalır), MCP üzerinden bağlı sistemlerinize giden token'ları da başkasının eline verebilir. Yapay zekâ yollarının sabit çekirdekte durması ve yenilerinin düzenli olarak denenmesi, saldırganların bu dosyaları aramaya değer bulduğunu gösteriyor. Gerçekten bulup bulmadıklarını bilmiyoruz.
Aynı haftalarda ikinci bir araç
22 Eylül – 7 Ekim arasında Araç A'nın da taradığı uygulamalardan birine, yine Google Cloud'dan başka bir araç geldi (Araç B):
- 12 IP, hepsi ABD Doğu (us-east1) ve Tayvan (asia-east1) bölgelerinde. Araç A'nın kullandığı Belçika bölgesinden hiç gelmedi.
- Beş tam tarayıcı kimliği: Chrome 131, Edge 130, Firefox 133, Safari/macOS ve Safari/iPhone. Aynı hedefe birkaç saniye içinde bu beş kimlikle istek gönderildi; yolların çoğu ikişer üçer kez tekrar istendi.
- Her dönemde birebir aynı liste:
- Aynı dönemdeki IP'lerin 4xx alan yol listeleri birebir aynı: 22–24 Eylül 18 yol, 25–29 Eylül 44 yol, 2–7 Ekim 74 yol.
- Dönemler arasındaki farkın en azından bir kısmı bizden kaynaklanıyor. 24 Eylül'de uzantılı yollar için de 404 döndürmeye başladık; 25 Eylül'den sonra eklenen 26 yolun hiçbiri nokta ile başlamıyor.
- Ekimde WAF'ta tam listesini gördüğümüz iki IP 132 farklı yol denedi. Bu liste Araç A'nın 112 yollu çekirdeğinin yalnızca 36'sını (%32) içeriyordu.
- Yapay zekâ yolu yok. Listesi daha çok
.bash_history,.pgpass,.pypirc,.vault-token,.kube/configgibi geliştirici ve sunucu dosyalarından oluşuyor.
İki aracın aynı kişi ya da gruba ait olup olmadığını bilmiyoruz.
Tek araç bu değil
İki araç, kayıtlarımızda görünen çok daha geniş bir taramanın parçası:
- 3 Ekim – 2 Kasım arasında 205 farklı IP, sistemlerimizde en az 10 farklı hassas yol denedi. Bunların 110'u (%54) Google Cloud adreslerindendi; 42'si Araç A'ydı. Bu IP'lerin aşağıdaki sorgudaki yollara gönderdiği isteklerin %92'si WAF'ta durdu.
- Ağustosta üçüncü bir araç, yine Google Cloud adreslerinden, yol kodlama hileleriyle (
/%2eenv,..%252F..%252F.env,/proc/self/environ) aynı işi yaptı:- Kendini 20'den fazla farklı bot olarak tanıttı; aralarında ChatGPT-User, GPTBot, OAI-SearchBot, ClaudeBot, Claude-User, PerplexityBot, Amazonbot ve Meta'nın tarayıcısı vardı.
- Google-Extended kimliğini bile kullandı. Oysa bu yalnızca robots.txt'te kullanılan bir belirteç; hiçbir gerçek istek bu kimlikle gelmez.
- Beş IP'nin her biri aynı 17 yapay zekâ yolunu denedi:
/.cursor/mcp.json,/.mcp.json,/.claude.json,/claude_desktop_config.json,/.codex/config.toml,/.aider.conf.yml,/.continue/config.jsonve diğerleri.
- 2 Kasım'da gelen başka bir araç neredeyse her istekte kimlik değiştirdi (187 istekte 158 farklı kimlik). Bunların bir kısmı Censys, LeakIX, ZoomEye, Shodan ve Palo Alto Expanse gibi internet tarama hizmetlerini taklit ediyordu.
Ders: Gerçek botlar yüzlerce gizli dosya yolunu art arda denemez. Bir bot kimliğine güvenmeden önce, sağlayıcının yayımladığı IP listeleriyle ya da ters DNS ile doğrulayın.
Bizde ne işe yaradı, ne yaramadı
İşe yaradı:
- Kenarda kurallar.
- Araç A'nın 42 IP'si ekim–kasımda 11.962 istek gönderdi; bunların 8.274'ü (%69) WAF'ta durdu.
- Engellenen isteklerin 4.191'ini, nokta ile başlayan yol bölümlerini ve bilinen gizli dosya yollarını engelleyen kendi kuralımız durdurdu.
- Bulunacak bir şey olmaması.
- WAF'tan geçen istekler 404 ya da uygulamanın boş kabuğunu aldı.
- Olay incelemelerinde, 200 dönen yanıtların ana sayfa olduğunu boyut ve MD5 özetiyle doğruladık.
- JavaScript paketlerimizde anahtar olmadığını ayrıca taradık.
İşe yaramadı ya da geç kaldı:
- SIEM görünürlüğü.
- Ekim–kasımdaki 83 oturumun yalnızca 12'si Wazuh'ta alarm üretti. Aracın 42 adresinden 31'i ekim–kasımda SIEM'e hiç düşmedi.
- Bu oturumlar ya web kaydını o tarihte SIEM'e almadığımız hedeflere geldi ya da WAF bütün isteklerini durdurduğu için sunucuya hiç ulaşmadı.
- Ders: WAF kayıtlarını da SIEM'e alın.
- IP engelleme.
- Taramaların yarısı 2,5 saniyeden önce bitiyor; alarm, karar ve engel zinciri ne kadar hızlı olursa olsun o tarama çoğu zaman çoktan bitmiş oluyor.
- ALB gibi uygulama katmanında çalışan bir yük dengeleyicinin arkasında, sunucudaki yerel güvenlik duvarı kuralı trafiği durdurmaz: paketler istemciden değil, yük dengeleyiciden gelir. Sunucunuz gerçek istemci IP'sini kaydetmiyorsa daha da kötüsü olur: otomatik engel yük dengeleyicinin kendi adresini engelleyip kesintiye yol açabilir.
- Engel o taramayı durdurmaz ama geri dönüşleri durdurabilir: 83 oturumun 41'i daha önce görülmüş bir IP'den geldi.
- Her taramadan sonra IP'yi engellediğimizi varsayarsak:
- 30 dakikalık engel (bizim sunucu kuralımızın süresi) bunların hiçbirini durdurmazdı.
- 24 saatlik bir engel 16'sını keserdi.
- 7 günlük bir WAF IP listesi 31'ini keserdi.
- Engeli yalnızca SIEM alarmına bağlasaydık, 7 günlük liste 31 değil 7 oturumu keserdi. Engeli WAF kayıtlarından tetikleyin.
- IP itibar listeleri, kısmen. AWS'nin yönetilen IP itibar listesi aracın 42 adresinden yalnızca 16'sını tanıdı (engellenen isteklerin %26'sı). Yeni kiralanan bulut IP'leri bu listelere geç girebiliyor.
- "Her şeye 200" (SPA tuzağı).
- Eylül ortasında bilinmeyen her yol için 200 koduyla ana sayfayı döndürüyorduk.
- Bu durumda tarama aracı "buldum" sanabilir, SIEM ise hiç hata görmediği için alarm üretmez.
- Uzantılı ve nokta ile başlayan yollar için 404 döndürmeye başladıktan sonra taramalar SIEM'de görünür oldu.
Kendi ortamınızda ne yapabilirsiniz
30 saniyelik kendi kendine test
SITE=https://siteniz.com
for yol in / /bu-yol-kesin-yok /.env /.git/config /.aws/credentials /.claude/settings.json /.cursor/mcp.json /docker-compose.yml /Dockerfile; do
printf '%-26s %s\n' "$yol" "$(curl -s -o /dev/null -w '%{http_code} %{size_download} bayt' "$SITE$yol")"
done
- İlk iki satır referanstır: ana sayfa ve var olmayan bir yol. Hassas yolların hepsi 404 (ya da 403) döndürmeli. 200 alıyorsanız boyutu ilk iki satırla karşılaştırın: aynıysa SPA tuzağındasınız; farklıysa dosya gerçekten yayında olabilir, hemen kaldırın ve içindeki anahtarları değiştirin.
- Testi sunucunuzun ham IP adresine (
curl -kile) ve varsayılan sanal sunucuya karşı da çalıştırın. Araç A bunları da taradı.
nginx
Aşağıdaki yapılandırmayı nginx 1.27.5 üzerinde test ettik. Denediğimiz 24 hassas yolun hepsi 404 aldı. Uygulamanın kendi sayfaları ve API'si etkilenmedi.
server {
# ...
# ACME doğrulaması: dosya yoksa 404 (SPA'ya düşmesin)
location ^~ /.well-known/acme-challenge/ { try_files $uri =404; }
# API: ^~ öneki aşağıdaki düzenli ifade kurallarının denenmesini engeller; hassas yollar burada ayrıca engellenir
location ^~ /api/ {
location ~ /\. { return 404; }
location ~* "^/api/(.*/)?(actuator|_profiler|phpinfo|server-info|server-status)" { return 404; }
proxy_pass http://uygulama;
}
# Nokta ile başlayan bir yol bölümü içeren bütün istekler 404 (yalnız /.well-known/ serbest)
location ~ /\.(?!well-known/) { return 404; }
# Uzantısız ama bilinen hassas adlar ve yönetim uçları
location ~* "^/(dockerfile|jenkinsfile|procfile|makefile|credentials|env|id_rsa|id_ed25519|kubeconfig|phpinfo|server-info|server-status|actuator|_profiler|_cat|_cluster|_nodes|_users|_config|solr)(/|$)" { return 404; }
# Uzantılı yollar: dosya gerçekten varsa sunulur, yoksa 404 (index.html'e düşmez)
location ~* "\.[a-z0-9]{1,8}$" { try_files $uri =404; }
# Geri kalan her şey SPA'ya
location / { try_files $uri /index.html; }
}
Kullanmadan önce:
- Bu yapılandırma, dosyaları diskten sunulan bir SPA içindir. Uygulamanın tamamı bir arka uca yönlendiriliyorsa (Next.js, .NET, Node), uzantı kuralı statik dosyaları bozabilir; o durumda yalnızca nokta ve hassas ad kurallarını kullanın.
- İçinde nokta geçen SPA yolları (
/kullanici/ali.veli,/belge/v1.2) da 404 alır. - Yük dengeleyicinizin sağlık denetimi
/actuator/healthgibi bu kuralların engellediği bir uca gidiyorsa, o yolu öncelocation = /actuator/health { … }ile açın; tam eşleşme düzenli ifadelerden önce gelir.server-statusgibi izleme uçları için de aynısı geçerli. - Süslü parantez ya da noktalı virgül içeren düzenli ifadeleri tırnak içine alın; almazsanız nginx yapılandırmayı yüklemez (
nginx -thata verir).
AWS WAF
Nokta ile başlayan bir yol bölümü içeren istekleri kenarda yakalayan kural (/.well-known/ hariç). AWS'nin kapasite denetiminden geçti (32 WCU).
{
"Name": "gizli-dosya-yollari",
"Priority": 10,
"Statement": { "AndStatement": { "Statements": [
{ "ByteMatchStatement": { "SearchString": "/.", "FieldToMatch": { "UriPath": {} },
"TextTransformations": [ { "Priority": 0, "Type": "URL_DECODE" }, { "Priority": 1, "Type": "NORMALIZE_PATH" } ],
"PositionalConstraint": "CONTAINS" } },
{ "NotStatement": { "Statement": { "ByteMatchStatement": { "SearchString": "/.well-known/", "FieldToMatch": { "UriPath": {} },
"TextTransformations": [ { "Priority": 0, "Type": "URL_DECODE" }, { "Priority": 1, "Type": "NORMALIZE_PATH" } ],
"PositionalConstraint": "STARTS_WITH" } } } }
] } },
"Action": { "Count": {} },
"VisibilityConfig": { "SampledRequestsEnabled": true, "CloudWatchMetricsEnabled": true, "MetricName": "gizli-dosya-yollari" }
}
- Önce Count modunda birkaç gün izleyin; meşru bir yolu yakalamadığından emin olunca Block'a alın.
update-web-aclbütün kural listesini değiştirir. Önceget-web-aclile mevcut kuralları alın, bu kuralı ekleyin veLockTokenile gönderin.Prioritydeğeri mevcut bir kuralla çakışmasın.SearchStringbir ikili (blob) alandır; AWS CLI v2'ye düz metin vermek için--cli-binary-format raw-in-base64-outparametresini ekleyin.
WAF kayıtlarınızda Araç A'yı arayın (CloudWatch Logs Insights)
Bu sorgu, çekirdek listeden seçtiğimiz ve başka tarama araçlarında nadir görülen 10 yolu kullanıyor. Kendi kayıtlarımızda bir aylık trafikte yalnızca Araç A'nın 42 IP'sini buldu: bu IP'lerin her biri 10 yolun hepsini denedi, başka hiçbir IP 6'ya ulaşmadı.
fields httpRequest.clientIp as ip, httpRequest.uri as uri
| filter uri in ["/.claude/settings.local.json", "/.env.anthropic", "/.env.openai", "/.amplifyrc", "/aws-exports.js", "/sendgrid.env", "/runtime-config.js", "/env-config.js", "/.docker/laravel/app/.env", "/config/aws.yml"]
| stats count_distinct(uri) as imza_yolu, count(*) as istek, min(@timestamp) as ilk, max(@timestamp) as son by ip
| filter imza_yolu >= 6
| sort ilk asc
Genel gizli dosya taramalarını görmek için ikinci bir sorgu. Bizde 205 IP döndürdü: Araç A'nın 42'si, Araç B'nin WAF kaydı olan 2'si ve 161 başka adres.
fields @timestamp, httpRequest.clientIp as ip, httpRequest.uri as uri, action
| filter uri like /(?i)\/(\.|%2e)env|\/(\.|%2e)git\/config|\/(\.|%2e)aws\/credentials|\/(\.|%2e)claude\/settings|\/(\.|%2e)cursor\/mcp\.json/
| stats count_distinct(uri) as farkli_yol, count(*) as istek, sum(action = "BLOCK") as engellenen, min(@timestamp) as ilk, max(@timestamp) as son by ip
| filter farkli_yol >= 10
| sort istek desc
engellenensütunuistek'ten küçükse, o IP'nin bazı istekleri uygulamanıza kadar ulaşmış demektir; bu isteklere hangi yanıtın döndürüldüğünü uygulama kayıtlarından kontrol edin.- Sorgular, WAF kayıtları CloudWatch Logs'a gidiyorsa çalışır; kayıtlar S3'e gidiyorsa aynı mantığı Athena'da kurun. Kayıtları yalnızca engellenen isteklerle sınırlayan bir filtre varsa sayılar eksik çıkar.
Wazuh
- Wazuh'un hazır 31151 kuralı (aynı kaynaktan kısa sürede çok sayıda 4xx; kural tanımında 90 saniye içinde
frequency="14") bu taramaları yakalıyor, ama ancak web sunucunuz bilinmeyen yollar için gerçekten 404 döndürüyorsa (bkz. SPA tuzağı). - Engeli bütün web ACL'lerinizin paylaştığı bir WAF IP kümesine yazın ve en az birkaç gün tutun. Tetikleyiciyi WAF kayıtlarından alın, çünkü her tarama SIEM'e düşmüyor.
Geliştirme tarafında
- Web köküne proje klasörünü değil, yalnızca derleme çıktısını (
dist/,public/) koyun..claude/,.cursor/,.vscode/,.gemini/,.git/ve.env*dağıtım paketine hiç girmesin. .env*dosyalarını ve.claude/settings.local.jsongibi kişisel ayar dosyalarını.gitignore'a ekleyin. Paylaşılan.claude/settings.jsondepoda kalabilir, ama içinde anahtar olmamalı.- Anahtarları yapılandırma dosyalarına değil, bir gizli anahtar yöneticisine koyun. MCP yapılandırmalarında token'ı dosyaya yazmak yerine ortam değişkeniyle verin.
- Derleme sırasında ön yüz paketlerinde anahtar taraması yapın.
- Bir anahtarın açığa çıktığından şüpheleniyorsanız önce anahtarı değiştirin, sonra kayıtlara bakın.
Göstergeler
Bulut IP'leri sık el değiştirir. Bu adresleri kalıcı olarak engellemek yerine, aşağıdaki davranış imzasını WAF ya da kenar kayıtlarında çalışan bir tespit kuralına çevirmenizi öneririz.
Araç A'nın davranış imzası:
- Aynı kaynaktan bir dakikadan kısa sürede 110'dan fazla farklı gizli dosya yolu; aralarında yukarıdaki imza sorgusunun 10 yolu.
- Gizli dosya isteklerinde kesik kimlik
Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36veAccept-Encoding: gzip, deflate. Bu kimliği başka araçlar da kullandığı için tek başına yeterli değil.
Araç A'nın IP adresleri (43 adres; adresler tıklanamaz biçimde [.] ile yazıldı; tarihler UTC'ye göre; bölgeler, Google'ın yayımladığı IP aralıklarından 2 Kasım 2026'da doğrulandı):
IP ilk görülme son görülme bölge
35.205.254[.]119 2026-09-18 2026-10-19 europe-west1
34.38.113[.]44 2026-09-18 2026-10-20 europe-west1
34.62.82[.]165 2026-09-24 2026-09-24 europe-west1
34.52.229[.]253 2026-10-05 2026-10-05 europe-west1
34.77.137[.]207 2026-10-05 2026-10-05 europe-west1
34.78.213[.]249 2026-10-05 2026-10-05 europe-west1
34.140.234[.]80 2026-10-05 2026-10-08 europe-west1
35.189.229[.]134 2026-10-05 2026-10-13 europe-west1
34.140.132[.]132 2026-10-08 2026-10-11 europe-west1
34.79.51[.]100 2026-10-08 2026-10-22 europe-west1
34.52.133[.]111 2026-10-09 2026-10-09 europe-west1
35.205.88[.]64 2026-10-09 2026-10-24 europe-west1
34.156.249[.]47 2026-10-10 2026-10-10 europe-west1
34.52.150[.]124 2026-10-10 2026-10-10 europe-west1
34.62.189[.]80 2026-10-10 2026-10-20 europe-west1
35.241.178[.]74 2026-10-11 2026-10-11 europe-west1
207.175.194[.]102 2026-10-11 2026-10-18 europe-west1
207.175.220[.]59 2026-10-11 2026-10-24 europe-west1
34.53.184[.]30 2026-10-12 2026-10-30 europe-west1
34.79.12[.]228 2026-10-13 2026-10-23 europe-west1
35.240.100[.]200 2026-10-13 2026-10-24 europe-west1
34.156.22[.]151 2026-10-16 2026-10-17 europe-west1
34.62.250[.]35 2026-10-16 2026-10-17 europe-west1
136.65.74[.]74 2026-10-17 2026-10-17 us-central1
34.14.99[.]143 2026-10-17 2026-10-24 europe-west1
35.241.239[.]86 2026-10-18 2026-10-23 europe-west1
34.62.25[.]61 2026-10-18 2026-10-27 europe-west1
34.22.126[.]178 2026-10-19 2026-10-19 europe-west1
34.34.160[.]116 2026-10-19 2026-10-19 europe-west1
34.53.212[.]113 2026-10-19 2026-10-27 europe-west1
35.241.202[.]92 2026-10-20 2026-10-20 europe-west1
34.79.59[.]9 2026-10-20 2026-10-22 europe-west1
207.175.98[.]108 2026-10-22 2026-10-22 europe-west1
34.62.18[.]205 2026-10-22 2026-10-22 europe-west1
34.53.227[.]51 2026-10-22 2026-10-23 europe-west1
34.140.179[.]23 2026-10-23 2026-10-23 europe-west1
104.199.36[.]53 2026-10-28 2026-10-28 europe-west1
34.62.116[.]145 2026-10-30 2026-10-30 europe-west1
34.52.234[.]95 2026-11-01 2026-11-01 europe-west1
34.77.241[.]117 2026-11-01 2026-11-01 europe-west1
23.251.135[.]142 2026-11-02 2026-11-02 europe-west1
34.62.246[.]24 2026-11-02 2026-11-02 europe-west1
34.76.27[.]30 2026-11-02 2026-11-02 europe-west1
Araç B'nin IP adresleri (22 Eylül – 7 Ekim; hepsi SIEM kaydından, ikisinin WAF kaydı da var):
| Dönem | IP | Bölge |
|---|---|---|
| 22–24 Eylül | 34.75.172[.]231 · 34.80.89[.]28 · 104.155.231[.]26 | us-east1, asia-east1 |
| 25–29 Eylül | 35.231.170[.]94 · 34.81.122[.]163 · 34.138.59[.]13 · 34.23.9[.]107 · 35.201.136[.]76 | us-east1, asia-east1 |
| 2–7 Ekim | 35.190.129[.]55 · 34.80.69[.]73 · 34.138.20[.]242 · 136.108.44[.]83 | us-east1, asia-east1 |
İndirilebilir dosyalar:
MITRE ATT&CK eşlemesi
| Teknik | Gözlem |
|---|---|
| T1595.003 — Active Scanning: Wordlist Scanning | sabit çekirdek + dönen tema ile gizli dosya taraması |
| T1594 — Search Victim-Owned Websites | ana sayfanın ve JavaScript paketlerinin indirilmesi |
| T1589.001 — Gather Victim Identity Information: Credentials | açıkta kalmış kimlik bilgilerini toplama girişimi |
| T1552.001 — Unsecured Credentials: Credentials In Files | hedeflenen dosyalar; bir dosya bulunsaydı bu tekniğe geçilirdi |
Gözlediğimiz bütün taramalar girişim aşamasında kaldı. Wazuh, 31151 kuralını T1595.002 ile etiketliyor.
Yöntem, veri kaynakları ve sınırlar
Tanımlar:
- Oturum: Bir IP'nin bir saat içindeki istekleri.
- Hedef taraması: Bir oturumun tek bir ada ya da adrese giden kısmı. 83 oturumdan 100 hedef taraması çıkıyor.
Veri kaynakları:
- AWS WAF kayıtları, 3 Ekim – 2 Kasım 2026 (22:40 UTC'ye kadar). Uygulamalardan biri için ayrıca 4 Ağustos – 3 Eylül.
- SOC veri gölümüzdeki Wazuh alarmları, ağustos – kasım. Bu alarmlar 4xx alan isteklerin ham kayıt satırlarını (yol ve tarayıcı kimliği dahil) içeriyor.
- Olay inceleme notlarımız.
- 3 Eylül – 3 Ekim arasında WAF kaydımız yok. Eylül ayrıntıları alarm satırlarından ve inceleme notlarından geliyor.
Bir IP'yi hangi araca bağladık:
- Araç A:
- WAF kaydı olan dönemde, çekirdeğin ana sayfa dışındaki 111 yolundan en az 105'ini denemesi. Kesik kimliği kullanan 95 adresten 42'si bunu karşıladı; bir sonraki adres yalnızca 70 yolu denedi.
- Eylülde (WAF kaydı yokken) alarm satırlarında yalnızca kesik kimliği kullanması ve ekim çekirdeğinin sunucuya ulaşan yollarını büyük ölçüde içermesi: 34.38.113[.]44'ün 26 Eylül taraması %83, 34.62.82[.]165 %69.
- Araç B:
- Aynı beş tam kimliği kullanması.
- Aynı dönemdeki IP'lerin 4xx yol listelerinin birebir aynı olması.
- Ayrı tuttuklarımız: Benzer görünen ama bu ölçütleri karşılamayan adresler, örneğin 31 Ekim ve 2 Kasım'daki iki tarama (çekirdeğin %42–43'ü).
Çekirdeğin tanımı: Araç A'nın 100 hedef taramasının en az %70'inde görülen yollar. Eşik %50 ile %80 arasında nereye konursa konsun liste değişmiyor.
Okurken dikkat edilecekler:
- Alarm sayıları yalnızca WAF'tan geçip 4xx alan istekleri sayar; bu yüzden hedefe ve WAF ayarına göre değişir.
- "İlk görüldüğü gün", bir yolun Araç A'nın kayıtlarında ilk göründüğü gündür. Başka araçlar aynı yolu daha önce denemiş olabilir; örneğin
/.cursor/mcp.jsonağustosta üçüncü araçta da vardı. - 22 Ağustos'ta, gerçek istemcisini bilmediğimiz bir iç adresten gelen tek bir satırda da aynı kesik kimlik var. Bu yüzden 18 Eylül, bir IP adresine bağlayabildiğimiz ilk iz; kesin bir başlangıç değil.
- Taramaların kime ait olduğunu bilmiyoruz; bu yazı bir atıf iddiası taşımaz. Bu adresler saldırganın kiraladığı sanal makinelere ait olabilir. Bu bir Google Cloud açığı değildir.
Kaynaklar
- Unit 42 (Palo Alto Networks), "Leaked Environment Variables Allow Large-Scale Extortion Operation in Cloud Environments", Ağustos 2024 — https://unit42.paloaltonetworks.com/large-scale-cloud-extortion-operation/
- Sysdig, "EMERALDWHALE: 15k Cloud credentials stolen in operation targeting exposed Git config files", Ekim 2024 — https://sysdig.com/blog/emeraldwhale/
- Sysdig, "LLMjacking: Stolen Cloud Credentials Used in New AI Attack", Mayıs 2024 — https://sysdig.com/blog/llmjacking-stolen-cloud-credentials-used-in-new-ai-attack/
- Google Cloud IP aralıkları — https://www.gstatic.com/ipranges/cloud.json
- MITRE ATT&CK — T1595.003, T1594, T1589.001, T1552.001
Bu yazı, 113SEC'in yönettiği SOC'ta gerçek trafik üzerinde yapılan gözlemlere dayanır. Sorularınız ve kendi kayıtlarınızda gördüklerinizi paylaşmak için: info@113sec.com