Untuk meyakinkan beberapa, saya tidak menemukan bug dengan mengamati eksploitasi, saya tidak punya alasan untuk percaya itu telah dieksploitasi sebelum diungkapkan (meskipun tentu saja saya tidak bisa mengesampingkannya). Saya juga tidak menemukannya dengan melihat bash
kode.
Saya tidak bisa mengatakan saya ingat persis kereta pikiran saya saat itu.
Itu kurang lebih datang dari beberapa refleksi pada beberapa perilaku dari beberapa perangkat lunak yang saya temukan berbahaya (perilaku, bukan perangkat lunak). Jenis perilaku yang membuat Anda berpikir: itu tidak terdengar seperti ide yang bagus .
Dalam hal ini, saya merefleksikan konfigurasi umum ssh yang memungkinkan lewat variabel lingkungan yang tidak disanitis dari klien asalkan nama mereka dimulai LC_
. Idenya adalah agar orang dapat tetap menggunakan bahasa mereka sendiri ketika ssh
masuk ke mesin lain. Ide yang bagus sampai Anda mulai mempertimbangkan betapa rumitnya penanganan lokalisasi terutama ketika UTF-8 dimasukkan ke dalam persamaan (dan melihat seberapa buruk penanganannya oleh banyak aplikasi).
Kembali pada bulan Juli 2014, saya telah melaporkan kerentanan dalam penanganan lokalisasi glibc yang dikombinasikan dengan sshd
konfigurasi itu, dan dua perilaku berbahaya lainnya dari bash
shell
memungkinkan penyerang (terotentikasi) untuk meretas ke server git asalkan mereka dapat mengunggah file di sana dan bash
digunakan sebagai shell login dari pengguna git unix (CVE-2014-0475).
Saya berpikir itu mungkin ide yang buruk untuk digunakan bash
sebagai shell login dari pengguna yang menawarkan layanan lebih dari ssh, mengingat bahwa itu adalah shell yang cukup kompleks (ketika semua yang Anda butuhkan hanya menguraikan baris perintah yang sangat sederhana) dan telah mewarisi sebagian besar kesalahan desain dari ksh. Karena saya sudah mengidentifikasi beberapa masalah dengan bash
digunakan dalam konteks itu (untuk menafsirkan ssh ForceCommand
), saya bertanya-tanya apakah ada potensi lebih banyak di sana.
AcceptEnv LC_*
memungkinkan setiap variabel yang namanya dimulai dengan LC_
dan saya memiliki ingatan samar-samar bahwa bash
fungsi yang diekspor (fitur berbahaya meskipun pada saat berguna) menggunakan variabel lingkungan yang namanya seperti
myfunction()
dan bertanya-tanya apakah tidak ada sesuatu yang menarik untuk dilihat di sana.
Saya akan mengabaikannya dengan alasan bahwa hal terburuk yang bisa dilakukan seseorang adalah mendefinisikan ulang sebuah perintah LC_something
yang tidak bisa benar-benar menjadi masalah karena itu bukan nama perintah yang ada, tetapi kemudian saya mulai bertanya-tanya bagaimana bash
mengimpor variabel lingkungan tersebut.
Bagaimana jika variabel dipanggil LC_foo;echo test; f()
misalnya? Jadi saya memutuskan untuk melihat lebih dekat.
SEBUAH:
$ env -i bash -c 'zzz() { :;}; export -f zzz; env'
[...]
zzz=() { :
}
mengungkapkan bahwa ingatan saya salah bahwa variabel tidak dipanggil myfunction()
tetapi myfunction
(dan itu
nilai yang dimulai dengan ()
).
Dan tes cepat:
$ env 'true;echo test; f=() { :;}' bash -c :
test
bash: error importing function definition for `true;echo test; f'
mengkonfirmasi kecurigaan saya bahwa nama variabel tidak dibersihkan, dan kode dievaluasi pada saat startup .
Lebih buruk lagi, jauh lebih buruk, nilainya juga tidak bersih:
$ env 'foo=() { :;}; echo test' bash -c :
test
Itu berarti bahwa setiap variabel lingkungan dapat menjadi vektor.
Saat itulah saya menyadari luasnya masalah, mengkonfirmasi bahwa itu dapat dieksploitasi melalui HTTP juga ( HTTP_xxx
/ QUERYSTRING
... env vars), yang lain seperti layanan pemrosesan surat, kemudian DHCP (dan mungkin daftar panjang) dan melaporkannya (dengan hati-hati) .