ksmbd Saldırı Yüzeyi & SMB2/SMB3 Protokol Fuzzing (syzkaller)

Reading time: 8 minutes

tip

AWS Hacking'i öğrenin ve pratik yapın:HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking'i öğrenin ve pratik yapın: HackTricks Training GCP Red Team Expert (GRTE) Azure Hacking'i öğrenin ve pratik yapın: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks'i Destekleyin

Genel Bakış

Bu sayfa, syzkaller kullanarak Linux in-kernel SMB sunucusu (ksmbd) üzerinde pratik teknikleri özetler. Odak, yapılandırma yoluyla protokol saldırı yüzeyini genişletmek, SMB2 operasyonlarını zincirleyebilen durumlu bir harness oluşturmak, grammar-geçerli PDU'lar üretmek, mutasyonları zayıf-kapsanan kod yollarına yönlendirmek ve focus_areas ile ANYBLOB gibi syzkaller özelliklerinden faydalanmaktır. Orijinal araştırma belirli CVE'leri sıralasa da burada yeniden kullanılabilir metodolojiye ve kendi kurulumlarınıza uyarlayabileceğiniz somut parçacıklara vurgu yapıyoruz.

Hedef kapsam: SMB2/SMB3 over TCP. Kerberos ve RDMA, harness'i basit tutmak için kasıtlı olarak kapsam dışıdır.


Yapılandırma ile ksmbd Saldırı Yüzeyini Genişletme

Varsayılan olarak, minimal bir ksmbd kurulumu sunucunun büyük bölümlerini test edilmemiş bırakır. Sunucuyu ek parser/handler'lar üzerinden geçirip daha derin kod yollarına ulaşmak için aşağıdaki özellikleri etkinleştirin:

  • Global düzey
  • Durable handles
  • Server multi-channel
  • SMB2 leases
  • Paylaşıma-özel düzey
  • Oplocks (varsayılan olarak açık)
  • VFS objects

Bunları etkinleştirmek, şu modüllerde yürütmeyi artırır:

  • smb2pdu.c (komut parse/dispatch)
  • ndr.c (NDR encode/decode)
  • oplock.c (oplock request/break)
  • smbacl.c (ACL parse/uygulama)
  • vfs.c (VFS ops)
  • vfs_cache.c (lookup cache)

Notlar

  • Tam seçenekler dağıtımınızın ksmbd userspace'ine (ksmbd-tools) bağlıdır. Durable handles, leases, oplocks ve VFS objects'i etkinleştirmek için /etc/ksmbd/ksmbd.conf ve paylaşıma özel bölümleri inceleyin.
  • Multi-channel ve durable handles durum makinelerini ve ömürleri değiştirir; bu genellikle concurrency altında UAF/refcount/OOB hatalarını yüzeye çıkarır.

Fuzzing için Kimlik Doğrulama ve Rate-Limiting Ayarları

SMB3 geçerli bir session gerektirir. Harness'lerde Kerberos uygulamak karmaşıklık eklediği için fuzzing için NTLM/guest tercih edin:

  • Guest erişimine izin verin ve map to guest = bad user olarak ayarlayın ki bilinmeyen kullanıcılar GUEST'e düşsün.
  • NTLMv2'yi kabul edin (kapalıysa policy'yi patch'leyin). Bu, handshake'i basit tutarken SMB3 kod yollarını çalıştırır.
  • Deneyler sırasında katı credit kontrollerini patch'leyin (CVE-2024-50285 için yapılan hardening sonrasında simultaneous-op kredilendirme daha katı hale geldi). Aksi takdirde rate-limit'ler fuzz edilmiş dizileri çok erken reddedebilir.
  • Yüksek verimli fuzzing sırasında erken reddi önlemek için max connections'ı (ör. 65536) artırın.

Dikkat: Bu gevşetmeler yalnızca fuzzing'i kolaylaştırmak içindir. Bu ayarlarla üretimde dağıtmayın.


Durumlu Harness: Kaynak Çıkarma ve İstekleri Zincirleme

SMB durumludur: birçok istek önceki yanıtlarda döndürülen tanımlayıcılara bağlıdır (SessionId, TreeID, FileID çiftleri). Harness'iniz yanıtları parse etmeli ve aynı program içinde ID'leri yeniden kullanarak daha derin handler'lara ulaşmalıdır (ör. smb2_create → smb2_ioctl → smb2_close).

Aşağıda bir yanıt buffer'ını işlemek (ilk +4B NetBIOS PDU uzunluğunu atlayarak) ve ID'leri önbelleğe almak için örnek bir snippet:

c
// process response. does not contain +4B PDU length
void process_buffer(int msg_no, const char *buffer, size_t received) {
uint16_t cmd_rsp = u16((const uint8_t *)(buffer + CMD_OFFSET));
switch (cmd_rsp) {
case SMB2_TREE_CONNECT:
if (received >= TREE_ID_OFFSET + sizeof(uint32_t))
tree_id = u32((const uint8_t *)(buffer + TREE_ID_OFFSET));
break;
case SMB2_SESS_SETUP:
// first session setup response carries session_id
if (msg_no == 0x01 && received >= SESSION_ID_OFFSET + sizeof(uint64_t))
session_id = u64((const uint8_t *)(buffer + SESSION_ID_OFFSET));
break;
case SMB2_CREATE:
if (received >= CREATE_VFID_OFFSET + sizeof(uint64_t)) {
persistent_file_id = u64((const uint8_t *)(buffer + CREATE_PFID_OFFSET));
volatile_file_id   = u64((const uint8_t *)(buffer + CREATE_VFID_OFFSET));
}
break;
default:
break;
}
}

İpuçları

  • Kimlik doğrulama/durumu paylaşan tek bir fuzzer süreci tutun: ksmbd’nin global/session tabloları ile daha iyi stabilite ve kapsama. syzkaller yine ops’ları async işaretleyerek eşzamanlılık enjekte eder, dahili olarak yeniden çalıştırır.
  • Syzkaller’in deneysel reset_acc_state’i global state’i sıfırlayabilir ama ağır yavaşlamaya neden olabilir. Bunun yerine stabiliteyi tercih edin ve fuzzing’e odaklanın.

Gramer Tabanlı SMB2 Oluşturma (Valid PDUs)

Microsoft Open Specifications içindeki SMB2 yapılarını bir fuzzer gramerine çevirin, böylece generator’ünüz yapısal olarak geçerli PDUs üretir ve bunlar sistematik olarak dispatcher’lara ve IOCTL handler’larına ulaşır.

Örnek (SMB2 IOCTL request):

smb2_ioctl_req {
Header_Prefix           SMB2Header_Prefix
Command                 const[0xb, int16]
Header_Suffix           SMB2Header_Suffix
StructureSize           const[57, int16]
Reserved                const[0, int16]
CtlCode                 union_control_codes
PersistentFileId        const[0x4, int64]
VolatileFileId          const[0x0, int64]
InputOffset             offsetof[Input, int32]
InputCount              bytesize[Input, int32]
MaxInputResponse        const[65536, int32]
OutputOffset            offsetof[Output, int32]
OutputCount             len[Output, int32]
MaxOutputResponse       const[65536, int32]
Flags                   int32[0:1]
Reserved2               const[0, int32]
Input                   array[int8]
Output                  array[int8]
} [packed]

Bu stil, structure sizes/offsets'ın doğru olmasını sağlar ve blind mutation'a kıyasla coverage'i dramatik şekilde iyileştirir.


Directed Fuzzing With focus_areas

syzkaller'in deneysel focus_areas özelliğini, şu anda coverage'i zayıf olan belirli functions/files üzerinde ağırlık vermek için kullanın. Örnek JSON:

json
{
"focus_areas": [
{"filter": {"functions": ["smb_check_perm_dacl"]}, "weight": 20.0},
{"filter": {"files": ["^fs/smb/server/"]}, "weight": 2.0},
{"weight": 1.0}
]
}

Bu, smbacl.c içindeki arithmetic/overflow yollarına isabet eden geçerli ACLs oluşturulmasına yardımcı olur. Örneğin, aşırı büyük bir dacloffset içeren kötü amaçlı bir Security Descriptor bir integer-overflow'ı yeniden üretir.

Reproducer builder (minimal Python):

python
def build_sd():
import struct
sd = bytearray(0x14)
sd[0x00] = 0x00; sd[0x01] = 0x00
struct.pack_into('<H', sd, 0x02, 0x0001)
struct.pack_into('<I', sd, 0x04, 0x78)
struct.pack_into('<I', sd, 0x08, 0x00)
struct.pack_into('<I', sd, 0x0C, 0x10000)
struct.pack_into('<I', sd, 0x10, 0xFFFFFFFF)  # dacloffset
while len(sd) < 0x78:
sd += b'A'
sd += b"\x01\x01\x00\x00\x00\x00\x00\x00"  # minimal DACL
sd += b"\xCC" * 64
return bytes(sd)

ANYBLOB ile Kapsama Platolarını Aşmak

syzkaller’s anyTypes (ANYBLOB/ANYRES), karmaşık yapıları genel olarak değişen blob'lara dönüştürmeyi sağlar. Kamuya açık SMB pcap'lerinden yeni bir corpus oluşturun ve payload'ları pseudo-syscall'unuzu çağıran syzkaller programlarına dönüştürün (ör. syz_ksmbd_send_req):

bash
# Extract SMB payloads to JSON
# tshark -r smb2_dac_sample.pcap -Y "smb || smb2" -T json -e tcp.payload > packets.json
python
import json, os
os.makedirs("corpus", exist_ok=True)

with open("packets.json") as f:
data = json.load(f)
# adjust indexing to your tshark JSON structure
packets = [e["_source"]["layers"]["tcp.payload"] for e in data]

for i, pkt in enumerate(packets):
pdu = pkt[0]
pdu_size = len(pdu) // 2  # hex string length → bytes
with open(f"corpus/packet_{i:03d}.txt", "w") as f:
f.write(
f"syz_ksmbd_send_req(&(&(0x7f0000000340))=ANY=[@ANYBLOB=\"{pdu}\"], {hex(pdu_size)}, 0x0, 0x0)"
)

Bu, keşfi hızlandırır ve kapsama birkaç puan artırırken hemen UAFs (ör. ksmbd_sessions_deregister içinde) tetikleyebilir.


Sanitizers: KASAN'ın Ötesi

  • KASAN, heap hataları (UAF/OOB) için birincil tespit aracıdır.
  • KCSAN genellikle bu hedefte yanlış pozitifler veya düşük şiddetli data races verir.
  • UBSAN/KUBSAN, KASAN'ın dizi indeks semantiği nedeniyle kaçırdığı declared-bounds hatalarını yakalayabilir. Örnek:
c
id = le32_to_cpu(psid->sub_auth[psid->num_subauth - 1]);
struct smb_sid {
__u8 revision; __u8 num_subauth; __u8 authority[NUM_AUTHS];
__le32 sub_auth[SID_MAX_SUB_AUTHORITIES]; /* sub_auth[num_subauth] */
} __attribute__((packed));

Setting num_subauth = 0 triggers an in-struct OOB read of sub_auth[-1], caught by UBSAN’s declared-bounds checks.


Verim ve Paralellik Notları

  • Tek bir fuzzer süreci (shared auth/state), ksmbd için genellikle çok daha kararlıdır ve syzkaller’in dahili async executor’ü sayesinde hala races/UAFs’i ortaya çıkarır.
  • Birden fazla VM ile yine de toplamda saniyede yüzlerce SMB komutuna ulaşabilirsiniz. Fonksiyon düzeyinde kapsama, fs/smb/server için ~%60 ve smb2pdu.c için ~%70 civarında elde edilebilir, ancak state-transition kapsaması bu tür metriklerle yeterince temsil edilmez.

Pratik Kontrol Listesi

  • ksmbd'de durable handles, leases, multi-channel, oplocks ve VFS objelerini etkinleştirin.
  • guest ve map-to-guest'e izin verin; NTLMv2'yi kabul edin. Fuzzer kararlılığı için credit limits'i patch'leyin ve max connections'ı yükseltin.
  • SessionId/TreeID/FileID'leri cache'leyen ve create → ioctl → close zincirleyen stateful bir harness oluşturun.
  • Yapısal geçerliliği korumak için SMB2 PDU'ları için bir grammar kullanın.
  • Zayıf kapsanan fonksiyonları ağırlıklandırmak için focus_areas kullanın (ör. smbacl.c yolları: smb_check_perm_dacl gibi).
  • Düzleşmeleri kırmak için gerçek pcaps'tan ANYBLOB ile seed verin; yeniden kullanım için seed'leri syz-db ile paketleyin.
  • KASAN + UBSAN ile çalıştırın; UBSAN declared-bounds raporlarını dikkatle triage edin.

Referanslar

  • Doyensec – ksmbd Fuzzing (Part 2): https://blog.doyensec.com/2025/09/02/ksmbd-2.html
  • syzkaller: https://github.com/google/syzkaller
  • ANYBLOB/anyTypes (commit 9fe8aa4): https://github.com/google/syzkaller/commit/9fe8aa4
  • Async executor change (commit fd8caa5): https://github.com/google/syzkaller/commit/fd8caa5
  • syz-db: https://github.com/google/syzkaller/tree/master/tools/syz-db
  • KASAN: https://docs.kernel.org/dev-tools/kasan.html
  • UBSAN/KUBSAN: https://docs.kernel.org/dev-tools/ubsan.html
  • KCSAN: https://docs.kernel.org/dev-tools/kcsan.html
  • Microsoft Open Specifications (SMB): https://learn.microsoft.com/openspecs/
  • Wireshark Sample Captures: https://wiki.wireshark.org/SampleCaptures
  • Arka plan okumaları: pwning.tech “Tickling ksmbd: fuzzing SMB in the Linux kernel”; Dongliang Mu’s syzkaller notes

tip

AWS Hacking'i öğrenin ve pratik yapın:HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking'i öğrenin ve pratik yapın: HackTricks Training GCP Red Team Expert (GRTE) Azure Hacking'i öğrenin ve pratik yapın: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks'i Destekleyin