Bagaimana kami menemukan kerentanan di server surat bank dan bagaimana hal itu mengancam

Kami sering melakukan tes penetrasi untuk bank dan lembaga keuangan lainnya. Kami juga sering menemukan kerentanan dari berbagai tingkat keparahan. Posting ini tentang salah satu kasus semacam itu.



Baru-baru ini, saat memeriksa keamanan sumber daya web bank, kami menemukan kerentanan di server email Exim 4.89, yang dapat mengakibatkan eksekusi kode jarak jauh. Kerentanan tersebut dikenal sebagai CVE-2018-6789. Dengan menggunakan eksploitasi PoC, kami mendapatkan Reverse Shell di mesin jarak jauh dan kemudian mengakses situs web bank.







Secara alami, kami bertanya-tanya mengapa eksploitasi kerentanan seperti itu menjadi mungkin.



Dari mana CVE-2018-6789 berasal?



Singkatnya, kerentanan ini disebabkan oleh kesalahan dalam menghitung panjang buffer di fungsi base64.c: b64decode yang digunakan oleh Exim. Anda dapat membaca lebih lanjut tentang ini di sini (dalam bahasa Inggris).



Jika Anda memasukkan string dengan panjang khusus, Anda dapat menimpa satu byte informasi dan, menggunakan tindakan sederhana, mengubah perintah server, sehingga menjalankan kode arbitrer (RCE).



Exim mengalokasikan buffer sebesar 3 * (len / 4) +1 byte untuk menyimpan data yang diterjemahkan. Namun, jika string base64 yang salah diumpankan ke input fungsi, misalnya, panjang 4n + 3, maka Exim akan mengalokasikan 3n + 1 byte untuk buffer. Tetapi itu akan menulis 3n + 2 byte data ke dalam buffer. Ini menyebabkan satu byte ditimpa di heap.



Exim menyediakan store_malloc_3 dan store_free_3, yang merupakan pembungkus untuk malloc dan fungsi gratis dari Glibc. Glibc mengalokasikan blok data yang besar, kemudian menyimpan metadatanya dalam 0x10 byte pertama dan mengembalikan pointer ke memori tempat pengguna dapat menulis datanya. Seperti inilah tampilannya:





Metadata mencakup ukuran blok sebelumnya (yang ada di memori di atas), ukuran blok saat ini, dan beberapa bendera. Tiga bit pertama dari ukuran tersebut digunakan untuk menyimpan bendera. Dalam contoh, ukuran 0x81 menyiratkan bahwa potongan saat ini adalah 0x80 byte dan potongan sebelumnya sudah digunakan.



Blok yang dibebaskan, setelah digunakan oleh Exim, ditempatkan dalam daftar tertaut ganda. Glibc mempertahankannya dengan menandai dan menggabungkan potongan bebas yang berdekatan menjadi potongan yang lebih besar untuk menghindari fragmentasi. Untuk setiap permintaan alokasi memori, Glibc memeriksa potongan ini dalam urutan FIFO dan menggunakannya kembali.





Untuk meningkatkan kinerja, Exim menggunakan add-on manajemen memori sendiri; itu didasarkan pada struktur blok penyimpanan. Fitur utama dari pemblokiran penyimpanan adalah masing-masing berukuran setidaknya 0x2000 byte, yang menjadi batasan untuk eksploitasi. Perhatikan bahwa pemblokiran penyimpanan juga memblokir data. Seperti inilah tampilannya di memori:





Perintah yang didukung oleh server email untuk mengatur data di heap:



  • EHLO hostname. EHLO hostname sender_host_name. , store_free store_malloc .
  • . , , Exim .
  • AUTH. Exim base64 . , store_get (). store_get().
  • Reset EHLO/HELO, MAIL, RCPT. , Exim smtp_reset. store_reset , ยซ ยป. , storeblock- store_get .




Untuk menggunakan heap overflow byte tunggal, kita harus dapat membebaskan blok data yang berada di bawah string yang didekodekan base64. Sender_host_name cocok untuk ini.



Heap perlu dibentuk sedemikian rupa untuk membiarkan blok data bebas di atas blok yang berisi sender_host_name.





Untuk melakukan ini, Anda perlu:



1. Menempatkan blok besar di tempat sampah yang tidak disortir. Pertama-tama, kami mengirim pesan EHLO dengan nama host yang terlalu besar sehingga ia mengalokasikan dan membebaskan potongan dengan panjang 0x6060 ke dalam bin yang tidak disortir.



2. Pilih blok penyimpanan pertama. Kemudian kami mengirim perintah yang tidak dikenal untuk memanggil store_get () dan mengalokasikan blok penyimpanan di dalam potongan yang dibebaskan.



3. Pilih blok kedua dan lepaskan yang pertama. Kami mengirim EHLO untuk menerima blok kedua. Blok pertama dibebaskan secara berurutan karena smtp_reset dipanggil setelah EHLO selesai.



Setelah heap disiapkan, kita dapat menggunakannya untuk menimpa ukuran blok asli. Kami memodifikasi 0x2021 menjadi 0x20f1, yang sedikit memperluas blok.







4. Kirim data base64 dan limpahkan 1 byte pada heap. Jalankan perintah AUTH untuk mengirim data base64.



5. Membuat dan mengirim string dengan ukuran yang sesuai. Sejak kami memperluas blok data, awal dari potongan berikutnya sekarang akan berada di suatu tempat di dalam. Sekarang kita perlu memperbaikinya untuk lulus pemeriksaan integritas Glibc. Kami mengirim string base64 lain di sini.



6. Bebaskan blok yang diperpanjang. Untuk mengontrol konten blok yang diperpanjang, kita perlu membebaskan blok terlebih dahulu, karena kita tidak dapat mengeditnya secara langsung. Artinya, kami harus mengirim pesan EHLO baru untuk membebaskan nama host lama. Namun, memproses perintah EHLO akan memanggil smtp_reset setelah eksekusi berhasil. Hal ini dapat menyebabkan gangguan program atau penghentian yang tidak normal. Untuk menghindari ini, kami mengirimkan nama host yang tidak valid seperti +.



7. Timpa penunjuk berikutnya dari blok penyimpanan yang tumpang tindih.





Setelah potongan dibebaskan, kita bisa mendapatkannya dengan AUTH dan menimpa bagian dari blok penyimpanan yang tumpang tindih. Di sini kami menggunakan teknik yang disebut "perekaman sebagian". Ini memungkinkan kita untuk mengubah pointer tanpa merusak ASLR. Kami telah mengubah sebagian penunjuk berikut ke blok yang berisi garis ACL. Garis ACL ditentukan oleh satu set global, seperti uschar * acl_smtp_helo;



Petunjuk ini diinisialisasi pada awal proses Exim dan disetel sesuai dengan konfigurasi. Misalnya, jika konfigurasi berisi baris acl_smtp_mail = acl_check_mail, penunjuk acl_smtp_mail menunjuk ke baris acl_check_mail.



Setiap kali server menerima perintah MAIL FROM, Exim melakukan pemeriksaan ACL, yang pertama kali memperluas acl_check_mail. Pada perluasan, jika Exim menemukan baris $ {run {cmd}}, Exim akan mencoba menjalankan perintah cmd, sehingga penyerang jarak jauh bisa mendapatkan kode untuk dieksekusi.



8. Setel ulang kunci penyimpanan dan dapatkan kunci penyimpanan yang berisi ACL. Blok ACL sekarang ada di blockchain. Ini akan dibebaskan setelah smtp_reset () selesai, dan kemudian kita bisa mengambilnya lagi dengan mengalokasikan beberapa blok.



9. Timpa baris ACL dan jalankan pemeriksaan ACL. Akhirnya, kami menulis ulang seluruh blok yang berisi garis ACL. Sekarang kami mengirim perintah seperti EHLO, MAIL, RCPT untuk menjalankan pemeriksaan ACL.



Omong-omong, eksploitasi kerentanan difasilitasi oleh ASLR dinonaktifkan untuk beberapa alasan yang tidak kami ketahui.



Masalah apa yang dimiliki pelanggan?



Yang pertama adalah kurangnya manajemen pembaruan. Karena fakta bahwa versi lama Exim digunakan, dimungkinkan untuk mengatur kompromi sistem. Untuk menghindari hal ini, kami menganjurkan agar Anda mengatur pemeriksaan rutin dan penginstalan pembaruan keamanan pada komponen infrastruktur informasi.



Kami merekomendasikan untuk memeriksa keamanan baru dan pembaruan penting setidaknya sebulan sekali. Untuk memeriksa pembaruan, lebih baik menggunakan situs / milis produsen peralatan atau informasi dari repositori.



Bank juga tidak memiliki proses manajemen kerentanan, itulah sebabnya kerentanan tidak terdeteksi tepat waktu. Penggunaan pemindai kerentanan khusus - misalnya, OpenVAS, Nessus, xSpider, dll. - akan membantu memperbaiki situasi.Pengujian penetrasi rutin dan pemantauan waktu penghapusan kerentanan juga akan membantu.



Dan yang tak kalah pentingnya. Bank tidak memiliki proses manajemen perubahan. Semua perubahan dibuat oleh administrator di lingkungan produksi. Akibatnya, tidak ada yang mengontrol atau memantau ini. Ini mengarah pada fakta bahwa ASLR dinonaktifkan di server.



Keluaran



Beberapa pelanggaran yang tampaknya tidak terkait mengakibatkan situs web bank disusupi. Ini dapat digunakan oleh penyerang untuk, misalnya, mengubah detail bank menjadi milik mereka sendiri.



Ceritanya berakhir dengan baik. Setelah kompromi, kami segera memberi tahu klien tentang situasinya. Bank segera memperbarui server Exim ke versi saat ini, yang kerentanannya tidak lagi relevan. Namun, jika kerentanan telah diidentifikasi bukan selama uji penetrasi, tetapi oleh penyerang sungguhan, hasilnya bisa berbeda.



All Articles