Neler yeni
Bughane Academy

Bughane Academy, bug bounty, web güvenliği ve sızma testi alanında kendini geliştirmek isteyenler için kurulmuş Türkçe odaklı bir topluluktur.

Burada; gerçek güvenlik açıkları, recon ve exploit teknikleri, payload & bypass yöntemleri, araçlar, scriptler ve write-up’lar topluluk tarafından paylaşılır ve tartışılır.

Birlikte öğren, birlikte üret, birlikte güçlen.

Analiz Rapor Otopsisi 2: Google'ın Kendi Destek Sisteminde 15.000$'lık PII Sızıntısı (ve "Fixed" Yalanı)

baldwin

Administrator
Katılım
1 Ocak 2026
Mesajlar
143
Tepkime puanı
180
Puan
43
Merhaba arkadaşlar

İkinci vakaya geçiyoruz. İlk yazıda hep "saldırgan ne yaptı" sorusuna bakmıştık. Bu kez tam tersi bir açıdan ilginç bir vaka seçtim: Google'ın kendisi bu raporu "düzelttik" diye kapatmış, ama araştırmacı dört ay sonra geri gelip "hayır, hala açık" demiş. Bu bana göre serinin en önemli derslerinden birini barındırıyor. bir raporun "Resolved" durumuna geçmesi, sorunun gerçekten bittiği anlamına gelmez.

Hedef de değişiyor: bu kez bir RCE veya memory corruption değil, Google'ın kendi müşteri destek altyapısında hiç yetkilendirme kontrolü olmayan global bir PII akışı.

Kaynak: michaeldalton.au/posts/hacking-google-support ve bughunters.google.com/reports/vrp/VBbY59QXh — halka açık, tüm teknik detaylar Google Bug Hunters ve araştırmacı (Michael Dalton) tarafından zaten yayınlanmış. Ben burada kendi yorumumu ve çıkardığım dersleri ekliyorum.

Bu Rapor Neden Beni Bu Kadar Etkiledi?

Bu yazıda birlikte şunlara bakacağız:
  • Google'ın "discovery document" mekanizmasının, gizli/dokümante edilmemiş API yüzeyini nasıl ortaya çıkardığı,
  • Bir endpoint'in URL'sinde "kaynak ID'si" olup olmamasının, arkasında yetkilendirme katmanı olup olmadığına dair nasıl bir sinyal verdiği,
  • Sıradan görünen bir "değişiklik listesi" endpoint'inin neden milyonlarca kaydı sızdırabildiği,
  • Ve "Google düzelttik dedi" ile "gerçekten düzeldi" arasındaki farkın neden araştırmacının kendi sorumluluğunda olduğu.

Önce Künyeye Bakalım

AlanDeğer
ProgramGoogle VRP (bughunters.google.com)
AraştırmacıMichael Dalton (bu, Google'da bulduğu ilk zafiyetiymiş)
Rapor başlığıReal-time Support API leaks PII of Google Support customers and deanonymises agents
Rapor IDb/421705403 (VBbY59QXh)
Google'ın iç önceliğiP1/S1 — "Nice catch!" notuyla kabul edilmiş
Zafiyet türüSensitive Data Exposure / Broken Access Control
Ödül$14.337 + $1.000 bonus (S2b: önemli güvenlik kontrolünün PII üzerinde bypass edilmesi)
Durum"Fixed" (10 Haziran 2025) → hâlâ açık (27 Eylül 2025) → gerçekten kapandı (12 Kasım 2025, 164 gün sonra)
İfşa tarihi31 Mart 2026

Önce Şu Kavramları Netleştirelim


clients6.google.com nedir?
Google, bazı dahili API'lerini `*.googleapis.com` yerine `*.clients6.google.com` üzerinden de sunuyor bu, `google.com` üzerindeki oturum çerezlerinin (cookie) ayrı bir token almaya gerek kalmadan doğrudan API kimlik doğrulaması için kullanılabilmesini sağlıyor (`SAPISIDHASH` şeması). Araştırmacı, destek chat widget'ının bu domain üzerinden bir iframe'de (`.../static/proxy.html`) çalıştığını fark ediyor bu tek başına bir kırmızı bayrak değil, ama "buraya bakmaya değer" sezgisini tetikliyor.

Discovery document nedir?
Google'ın API altyapısı son derece standartlaştırılmış: her servis, kendi metodlarını listeleyen bir "discovery document" sunar (`GET /$discovery/rest`). Bu belge resmi olarak dokümante edilmemiş olsa da, doğru bir API anahtarıyla istendiğinde tüm metod listesini döküyor.

Benim kuralım: Bir uygulamanın arayüzünde (UI) görünen özellik sayısı ile, altındaki API'nin gerçekte sunduğu metod sayısı arasında fark olduğunu varsayarım. UI sadece "kullanılan" yüzeyi gösterir; "var olan" yüzeyi görmek için API'nin kendi self-documentation mekanizmasına bakmak gerekir.

API anahtarı (API key), kimlik doğrulama değildir
Client-side JavaScript'te sabit kodlanmış bir API anahtarı bulmak (`AIzaSyB5V4SIBGmrqREm7kf2fBJgPcBMCdUrLzE`) tek başına bir zafiyet değil bu anahtar sadece "hangi GCP projesi bu isteği yapıyor" bilgisini taşır, kullanıcıyı yetkilendirmez. Asıl yetkilendirme (varsa) her metodun kendi içinde, sunucu tarafında uygulanmalı. Bu raporun can alıcı noktası tam olarak şu: bazı metodlarda bu kontrol var, bazılarında yok.

Peki Burada Tam Olarak Ne Bozuk?

93 metodluk discovery document'te dikkat çeken bir metod var: `changes.list`, açıklaması sadece şöyle: "Get list of changes for specified time period and pools."

Kod:
POST /v2/changes:list HTTP/2
Host: realtimesupport.clients6.google.com
Cookie: <redacted>
Authorization: SAPISIDHASH <redacted>
X-Goog-Api-Key: AIzaSyB5V4SIBGmrqREm7kf2fBJgPcBMCdUrLzE
Origin: https://support.google.com
Content-Type: application/json

{
  "includeInitialSnapshot": true,
  "timeRange": {
      "startTimestamp": "1735713335000",
      "endTimestamp": "1735713345000"
  }
}

Bu isteğin tek parametresi bir zaman aralığı hangi müşteriye, hangi case'e, hangi pool'a ait olduğuna dair hiçbir kısıtlama yok. Dönen yanıt, o zaman aralığında sistemde olan biten her şeyin global bir dökümü:

Kod:
{
  "initialSnapshot": {
    "phoneSupportRequestDiff": [{
      "phoneSupportRequestId": "00000000-0000-0000-0000-000000000000",
      "after": {
        "caseId": "6-1234567891234",
        "agentId": "01189998819991197253",
        "customerInformation": {
          "customerPhoneNumber": "+61 2 8503 8000"
        },
        "callType": "CALLBACK"
      }
    }],
    "agentDiff": [{
      "agentId": "01189998819991197253",
      "after": {
        "jid": "sergeybrin@google.com",
        "preferredName": "Sergey",
        "status": "AVAILABLE",
        "activityStatus": { "label": "Chat" }
      }
    }]
  }
}

(Yukarıdaki örnekte isim/telefon, yazarın kendi şaka niyetine kullandığı yer tutuculardır. gerçek müşteri verisi değildir.) Bozuk olan şey: bu endpoint'in hiçbir resource-level yetkilendirme kontrolü yok herhangi bir Google hesabıyla giriş yapan herkes, herhangi bir zaman aralığı için sistemdeki tüm ajan kimliklerini ve müşteri PII'sini çekebiliyor.

Araştırmacı Buraya Nasıl Geldi?

  1. Domain anomalisi: Destek widget'ının `clients6.google.com` üzerinde çalıştığını fark edip, bunun gizli bir private API olduğunu çıkarıyor.
  2. API anahtarını çıkarma: Client-side JS dosyasında sabit kodlanmış anahtarı buluyor.
  3. Yüzeyi büyütme: Discovery document ile 93 metod buluyor widget'ın arayüzü sadece 14'ünü kullanıyor, yani 79 metod hiç test edilmemiş, "kör nokta" durumunda.
  4. Sistematik tarama + örüntü tanıma: Minimal bir temel istek kurup discovery document'teki her metodu deniyor. Kritik gözlem: URL'sinde bir kaynak ID'si olan endpoint'ler (`/v2/agents/{agent_id}:pools`) hep 403 Permission Denied veriyor yani bir ara katman (middleware) bu ID'yi kontrol ediyor. Ama URL'sinde kaynak ID'si olmayan endpoint'ler farklı davranıyor: 400 Invalid Argument, yani istek daha ileri bir noktada başarısız oluyor.
  5. Önceliklendirme: "ID yok → farklı/daha zayıf kontrol noktası" örüntüsünü kırmızı bayrak olarak işaretleyip bu sınıftaki metodları önceliklendiriyor.

Benim genel ilkem: Bir API'de aynı sınıftaki farklı endpoint'ler farklı hata kodlarıyla başarısız oluyorsa (403 vs 400 gibi), bu genelde "aynı yetkilendirme katmanından geçmiyorlar" anlamına gelir. Hata kodu farkı, içeride farklı bir kod yolu olduğunun dışarıdan görülebilen izidir — tıpkı ilk yazımızdaki compile oracle mantığı gibi.

Peki Etkisi Ne Olabilirdi?

Araştırmacı sadece 4 başarılı çağrı yapıyor ve bundan, verinin en az Ocak-Haziran 2025 aralığını kapsadığını, ve tahminen en az 30 milyon case'a erişilebilir olduğunu çıkarıyor (Google tam sayıyı paylaşmamış, bu muhafazakar bir alt sınır).

İki ayrı PII sızıntısı iç içe geçiyor:
  • Ajan deanonymization: Gerçek ad, @google.com e-posta adresi, ve dakika dakika aktivite durumu ("Lunch", "Coaching", "Twitter Support" gibi etiketler) bu, bireysel ajanların mesai programının çıkarılabilmesi anlamına geliyor (stalking riski).
  • Müşteri PII'si: Telefon görüşmesi yapan her müşterinin redakte edilmemiş telefon numarası, hangi ajan ve case ile eşleştiği.

Yazarın vurguladığı ikincil risk bence en çarpıcı kısım: bir müşteri Google Destek ile bir görüşmeyi bitirdikten 10 saniye sonra, "az önce konuştuğunuz ajanın yöneticisi" diyen başka bir arama alabilir saldırgan hangi departmanla görüştüğünüzü, hangi ajanla konuştuğunuzu tam olarak biliyor. Bu, bu zafiyeti klasik bir PII sızıntısından çok daha güçlü bir vishing/sosyal mühendislik aracına çeviriyor.

Burada Durmak da Bir Beceridir

  • Sadece 4 başarılı çağrı yapmış, daha fazlasını denememiş.
  • `cbfConversationId` alanının chat içeriğine erişim sağlayabileceğini fark etmiş ama verinin hassasiyeti nedeniyle bunu denememiş.
  • Telefon çağrılarını transfer etme gibi başka olası aksiyonları da not etmiş ama test etmemiş.
  • Şokun ardından hemen, gece yarısından kısa süre sonra raporu yazmaya başlamış.

"Fixed" Demek Düzeldi Demek Değildir

İşte bu raporun asıl benzersiz dersi. Zaman çizelgesine bakalım:
  • 1 Haziran 2025: Rapor gönderiliyor.
  • 2 Haziran: Triyaj + P1/S1 olarak kabul ("Nice catch!").
  • 10 Haziran: Google $14.337 + $1.000 bonus ödül veriyor ve raporu kapatıyor.
  • 27 Eylül 2025: Araştırmacı zafiyeti yeniden test ediyor — hâlâ çalışıyor.
  • 29 Eylül: Google, ürün ekibinin kök sorunu hâlâ düzelttiğini doğruluyor.
  • 12 Kasım 2025: Rapor gerçekten "fixed" olarak kapanıyor — ilk rapordan 164 gün sonra.

Yani ödül verilmesi ile sorunun gerçekten ortadan kalkması arasında dört ay var, ve bu farkı ortaya çıkaran tek şey araştırmacının "kapandı" etiketine güvenmeyip kendi inisiyatifiyle yeniden test etmesi. Çoğu hunter ödülü alıp bir dahaki vakaya geçer — bu raporun bu kadar değerli olmasının sebeplerinden biri de bu disiplin.

Benim genel ilkem: Bir programın "resolved/fixed" etiketi benim için bir iddiadır kanıt değil. Özellikle yüksek etkili bulgularda fix'in yayına girdiği iddia edilen tarihten sonra bir kontrol turu atmak raporun gerçek değerini koruyor.

Benden Size Çıkarımlar

  1. Bir API'nin UI'da kullanılan kısmı ile gerçekte sunduğu tüm yüzey arasındaki farkı kapatın. discovery document, OpenAPI/Swagger şeması, GraphQL introspection gibi self-documentation mekanizmaları bu farkı ücretsiz olarak gösterir.
  2. Aynı API ailesindeki endpoint'ler arasında hata kodu/davranış farkı arıyorsanız, bu genelde "hangi kod yolundan geçtiği" konusunda dışarıdan görülebilen bir sinyaldir.
  3. "Bu endpoint URL'sinde hangi kaynağa ait olduğunu belirten bir parametre yok" gözlemini, "o zaman kim sahibi olduğunu nasıl kontrol ediyor?" sorusuna çevirin. çoğu zaman cevap kontrol etmiyor olur.
  4. Bulduğunuz primitive'i kanıtlamak için en az veriyi çekin, daha hassas alanlara (örn. chat içeriği) gerek olmadıkça dokunmayın.
  5. Bir rapor "fixed" olarak kapandığında işiniz bitmiş sayılmaz. özellikle yüksek etkili bulgularda, birkaç ay sonra geri dönüp doğrulamak, hem etik hem de profesyonel bir alışkanlıktır.

İki yazıda da aynı iskelet tekrar ediyor: şüpheli bir asimetri/eksiklik bul, en ucuz deneyle kanıtla, kanıtladığın kadarını raporla ve bu kez ek olarak, kapandığını iddia ettikleri an'a da güvenme. Bir dahaki vakada görüşmek üzere.

Bu yazı, michaeldalton.au/posts/hacking-google-support ve bughunters.google.com/reports/vrp/VBbY59QXh kaynaklarının kamuya açık metninden derlenmiştir.
 
Geri
Üst