Reverse kategorisindeki orta zorluktaki RevOne'a yakından bakalım. Elf formatındaki executeable dosyamızı indirip çalıştırıdığımızda kullanıcı adı ve parola istemekte eğer girdiler yanlış ise
"Wrong username or password -_-" mesajı ile sonlanıyor . Binwalk aracı ile dosyanın entropisine ve içeriğine baktığımızda dosyada herhangi bir şifreleme vb. görülmemekte .
Ghidra ile dosyamızı açıyoruz ve main fonksiyonundan incelemeye başlıyoruz. Açtığımızda koşullar ve döngüler görmekteyiz.Kodu daha iyi anlamak için
L kısayolu ile değişkenlerin isimlerini değiştiriyoruz.Aşşağıdaki gibi bir kod ortaya çıkardık .
undefined8 main(void)
{
byte bVar1;
bool bVar2;
size_t username_length;
byte *pbVar3;
undefined *puVar4;
basic_ostream *pbVar5;
char *pcVar6;
ulong index;
undefined8 local_468;
undefined8 local_460;
basic_string<char,std::char_traits<char>,std::allocator<char>> local_458 [32];
byte password [4];
char parola_karakter_5;
char parola_karakter_6;
char parola_karakter_7;
char parola_karakter_8;
char parola_karakter_9;
char parola_karakter_10;
char parola_karakter_11;
char parola_karakter_12;
char parola_karakter_13;
char parola_karakter_14;
char parola_karakter_15;
char username [518];
allocator<char> local_32;
undefined local_31;
basic_string<char,std::char_traits<char>,std::allocator<char>> *local_30;
ulong local_28;
int i;
char degisken_bir;
banner();
printf(" Enter your name\n > ");
std::operator>>((basic_istream *)std::cin,username);
printf(" Enter password\n > ");
std::operator>>((basic_istream *)std::cin,(char *)password);
i = 0;
while( true ) {
index = (ulong)i;
username_length = strlen(username);
if (username_length <= index) break;
if (username[i] == '_') {
degisken_bir = '\x01';
}
i = i + 1;
}
if (degisken_bir == '\x01') {
username_length = strlen(username);
if (6 < username_length) goto LAB_001013b9;
}
hatavar();
LAB_001013b9:
username_length = strlen((char *)password);
if (username_length < 0xf) {
hatavar();
}
.
.
.
LAB_001013b9: etiketine kadar olan kısımda kullanıcı adı kontrol ediliyor . Algoritmayı anlamaya çalışalım While döngüsü her döndüğünde :
- index değişkenine i değişkeni atanıyor
- username_length değişkenine kullanıcı adının uzunluğu atanıyor
- username_length değişkeninin uzunluğu küçük eşit index ise(yani girilen kullanıcı adının uzunluğu kadar döngü çalışmış ise) while döngüsünden çık
- Karakter _ ise degisken_1'e 0x01 değerini ata
- i değişkenine 1 ekle
- Başa dön
Bu algoritmayı cpp ile yazıp çalıştırdığımızda geçerli kullanıcı adını buluyoruz . Kullanıcı adında
_ karakterinin olması ve uzunluğunun 6 karakterden büyük olması istenmekte . Bu şekilde kullanıcı adını elde etmiş olduk .
Sıra parola kısmına geldi .
LAB_001013b9:
username_length = strlen((char *)password);
if (username_length < 0xf) {
hatavar();
}
if (parola_karakter_6 != 'i') {
hatavar();
}
if (parola_karakter_12 != 'P') {
hatavar();
}
if (password[0] != 0x50) {
hatavar();
}
if (password[1] != '4') {
hatavar();
}
if (password[3] != 's') {
hatavar();
}
if (password[2] != 's') {
hatavar();
}
if (parola_karakter_5 != 'H') {
hatavar();
}
if (parola_karakter_7 != 'd') {
hatavar();
}
if (parola_karakter_8 != 'd') {
hatavar();
}
if (parola_karakter_9 != 'e') {
hatavar();
}
if (parola_karakter_10 != 'n') {
hatavar();
}
if (parola_karakter_13 != 'a') {
hatavar();
}
if (parola_karakter_14 != 's') {
hatavar();
}
if (parola_karakter_15 != 's') {
hatavar();
}
if (parola_karakter_11 != '_') {
hatavar();
}
Kullanıcı adı aşamasında belirtilen 6 karakterden uzun olma şartı , parola kontrol kısımda 15 karakterden uzun olma şartı koşulmuş . Burada dikkat etmemiz gereken nokta
byte password [4]; 4 bytle'lık parola değişkeni oluşturulmuş . 4 karakterden fazla girildiğinde overflow gerçekleşiyor . Statik değişkenler stack üzerinde yan yana tutulduğundan girilen fazlalık değerler password değişkenin yanındaki değişkenlerin alanlarına yazılıyor . Yani 4 karakterden sonraki karakterler değişkenlerin tanımlanma sıralarına göre sıraayla atanmış oluyor .
Olayın anlaşılması açısından aşağıdaki cpp kodunda kullanıcıdan girdi alınıyor alınan girdi 4 byte'dan fazla olduğu için devamında tanımlanan değişkenlere taşma gerçekleşiyor . Yani 16 karakterlik parola girdiğimizde 12 tanesi diğer değişkenlere taşmış olacak.
Bu koşulları takip ederek sonuca ulaşıyoruz .
No comments:
Post a Comment