PENOLAKAN : Jawaban ini ditulis pada tahun 2008.
Sejak itu, PHP telah memberi kami password_hash
dan password_verify
, dan sejak diperkenalkan, mereka adalah metode hashing & checking kata sandi yang direkomendasikan.
Teori jawabannya masih bagus untuk dibaca.
TL; DR
Larangan
- Jangan batasi karakter apa yang dapat dimasukkan oleh pengguna untuk kata sandi. Hanya orang idiot yang melakukan ini.
- Jangan batasi panjang kata sandi. Jika pengguna Anda menginginkan kalimat dengan supercalifragilisticexpialidocious di dalamnya, jangan mencegah mereka menggunakannya.
- Jangan menghapus atau melepaskan HTML dan karakter khusus dalam kata sandi.
- Jangan pernah menyimpan kata sandi pengguna Anda dalam teks biasa.
- Jangan pernah mengirim email kata sandi kepada pengguna Anda kecuali jika kata sandi itu hilang, dan Anda mengirimnya sementara.
- Tidak pernah, pernah login kata sandi dengan cara apa pun.
- Kata sandi hash dengan SHA1 atau MD5 atau bahkan SHA256! Kerupuk modern dapat melebihi 60 dan 180 miliar hash / detik (masing-masing).
- Jangan mencampur bcrypt dan dengan output mentah dari hash () , baik gunakan output hex atau base64_encode itu. (Ini berlaku untuk input apa pun yang mungkin memiliki gangguan
\0
di dalamnya, yang dapat melemahkan keamanan dengan serius.)
Dos
- Gunakan scrypt ketika Anda bisa; bcrypt jika Anda tidak bisa.
- Gunakan PBKDF2 jika Anda tidak dapat menggunakan bcrypt atau scrypt, dengan hash SHA2.
- Setel ulang kata sandi semua orang ketika basis data dikompromikan.
- Menerapkan panjang minimum 8-10 karakter yang wajar, ditambah membutuhkan setidaknya 1 huruf besar, 1 huruf kecil, angka, dan simbol. Ini akan meningkatkan entropi kata sandi, yang pada gilirannya membuatnya lebih sulit untuk dipecahkan. (Lihat bagian "Apa yang membuat kata sandi yang baik?" Untuk beberapa perdebatan.)
Kenapa sih kata sandi hash?
Tujuan di balik hashing passwords sederhana: mencegah akses berbahaya ke akun pengguna dengan membahayakan basis data. Jadi tujuan dari hashing kata sandi adalah untuk mencegah seorang hacker atau cracker dengan biaya terlalu banyak waktu atau uang untuk menghitung kata sandi teks biasa. Dan waktu / biaya adalah pencegah terbaik dalam gudang senjata Anda.
Alasan lain Anda menginginkan hash yang baik dan kuat di akun pengguna adalah memberi Anda cukup waktu untuk mengubah semua kata sandi dalam sistem. Jika database Anda dikompromikan, Anda akan memerlukan waktu yang cukup untuk setidaknya mengunci sistem, jika tidak mengubah setiap kata sandi dalam database.
Jeremiah Grossman, CTO dari Whitehat Security, menyatakan di blog White Hat Security setelah pemulihan kata sandi baru-baru ini yang membutuhkan kekerasan terhadap proteksi kata sandi:
Menariknya, dalam menjalani mimpi buruk ini, saya belajar BANYAK yang tidak saya ketahui tentang pemecahan kata sandi, penyimpanan, dan kompleksitas. Saya menghargai mengapa penyimpanan kata sandi jauh lebih penting daripada kompleksitas kata sandi. Jika Anda tidak tahu bagaimana kata sandi Anda disimpan, maka yang benar-benar dapat Anda andalkan adalah kompleksitas. Ini mungkin pengetahuan umum untuk kata sandi dan pro kripto, tetapi untuk rata-rata InfoSec atau pakar Keamanan Web, saya sangat meragukannya.
(Penekanan milikku.)
Apa yang membuat kata sandi yang baik ?
Entropi . (Bukannya aku sepenuhnya berlangganan sudut pandang Randall.)
Singkatnya, entropi adalah seberapa banyak variasi dalam kata sandi. Ketika kata sandi hanya huruf kecil roman, itu hanya 26 karakter. Itu tidak banyak variasi. Kata sandi alfa-numerik lebih baik, dengan 36 karakter. Tetapi memungkinkan huruf besar dan kecil, dengan simbol, kira-kira 96 karakter. Itu jauh lebih baik dari sekedar surat. Satu masalah adalah, untuk membuat kata sandi kita mudah diingat, kita memasukkan pola — yang mengurangi entropi. Ups!
Entropi kata sandi diperkirakan dengan mudah. Menggunakan berbagai karakter ascii (kira-kira 96 karakter yang dapat diketik) menghasilkan entropi 6,6 per karakter, yang pada 8 karakter untuk kata sandi masih terlalu rendah (52,679 bit entropi) untuk keamanan di masa depan. Tetapi kabar baiknya adalah: kata sandi yang lebih panjang, dan kata sandi dengan karakter unicode, benar-benar meningkatkan entropi kata sandi dan membuatnya lebih sulit untuk dipecahkan.
Ada diskusi yang lebih panjang tentang entropi kata sandi di situs Crypto StackExchange . Pencarian Google yang baik juga akan menghasilkan banyak hasil.
Dalam komentar saya berbicara dengan @popnoodles, yang menunjukkan bahwa menegakkan kebijakan kata sandi dengan panjang X dengan X banyak huruf, angka, simbol, dll, sebenarnya dapat mengurangi entropi dengan membuat skema kata sandi lebih dapat diprediksi. Saya setuju. Randomess, senyata mungkin, selalu merupakan solusi teraman tetapi paling tidak diingat.
Sejauh yang saya tahu, membuat kata sandi terbaik di dunia adalah Catch-22. Entah itu tidak berkesan, terlalu dapat diprediksi, terlalu pendek, terlalu banyak karakter unicode (sulit untuk mengetik pada perangkat Windows / Mobile), terlalu lama, dll. Tidak ada kata sandi yang cukup baik untuk tujuan kita, jadi kita harus melindunginya seolah-olah mereka berada di Fort Knox.
Praktik terbaik
Bcrypt dan scrypt adalah praktik terbaik saat ini. Scrypt akan lebih baik daripada bcrypt dalam waktu, tetapi belum melihat adopsi sebagai standar oleh Linux / Unix atau oleh webservers, dan belum memiliki ulasan mendalam tentang algoritma yang diposting. Tapi tetap saja, masa depan algoritma memang terlihat menjanjikan. Jika Anda bekerja dengan Ruby ada permata scrypt yang akan membantu Anda, dan Node.js sekarang memiliki paket scrypt sendiri . Anda dapat menggunakan Scrypt dalam PHP baik melalui ekstensi Scrypt atau ekstensi Libsodium (keduanya tersedia dalam PECL).
Saya sangat menyarankan membaca dokumentasi untuk fungsi crypt jika Anda ingin memahami cara menggunakan bcrypt, atau menemukan diri Anda pembungkus yang baik atau menggunakan sesuatu seperti PHPASS untuk implementasi yang lebih lama. Saya merekomendasikan minimal 12 putaran bcrypt, jika tidak 15 hingga 18.
Saya berubah pikiran tentang menggunakan bcrypt ketika saya mengetahui bahwa bcrypt hanya menggunakan jadwal kunci blowfish, dengan mekanisme biaya variabel. Yang terakhir memungkinkan Anda meningkatkan biaya untuk memaksa kata sandi dengan meningkatkan jadwal kunci blowfish yang sudah mahal.
Praktek rata-rata
Saya hampir tidak bisa membayangkan situasi ini lagi. PHPASS mendukung PHP 3.0.18 hingga 5.3, sehingga dapat digunakan di hampir setiap instalasi yang dapat dibayangkan — dan harus digunakan jika Anda tidak tahu pasti bahwa lingkungan Anda mendukung bcrypt.
Tetapi misalkan Anda tidak dapat menggunakan bcrypt atau PHPASS sama sekali. Lalu bagaimana?
Coba implementasi PDKBF2 dengan jumlah putaran maksimum yang dapat ditoleransi oleh lingkungan / aplikasi / persepsi pengguna Anda. Angka terendah yang saya sarankan adalah 2500 putaran. Juga, pastikan untuk menggunakan hash_hmac () jika tersedia untuk membuat operasi lebih sulit untuk direproduksi.
Praktek Masa Depan
Datang dalam PHP 5.5 adalah pustaka perlindungan kata sandi lengkap yang menghilangkan segala kesulitan bekerja dengan bcrypt. Sementara sebagian besar dari kita terjebak dengan PHP 5.2 dan 5.3 di lingkungan yang paling umum, terutama host bersama, @ircmaxell telah membangun lapisan kompatibilitas untuk API yang akan datang yang kompatibel dengan PHP 5.3.7.
Rekap Kriptografi & Penafian
Kekuatan komputasi yang diperlukan untuk benar-benar memecahkan kata sandi hash tidak ada. Satu-satunya cara bagi komputer untuk "memecahkan" kata sandi adalah membuatnya kembali dan mensimulasikan algoritma hashing yang digunakan untuk mengamankannya. Kecepatan hash secara linear terkait dengan kemampuannya untuk menjadi kasar. Lebih buruk lagi, sebagian besar algoritma hash dapat dengan mudah diparalelkan untuk melakukan lebih cepat. Inilah sebabnya mengapa skema mahal seperti bcrypt dan scrypt sangat penting.
Anda tidak mungkin dapat melihat semua ancaman atau jalan serangan, dan karenanya Anda harus melakukan upaya terbaik untuk melindungi pengguna Anda di muka . Jika tidak, maka Anda bahkan mungkin kehilangan fakta bahwa Anda diserang sampai terlambat ... dan Anda bertanggung jawab . Untuk menghindari situasi itu, mulailah bertindak paranoid. Serang perangkat lunak Anda sendiri (secara internal) dan berupaya mencuri kredensial pengguna, atau memodifikasi akun pengguna lain atau mengakses data mereka. Jika Anda tidak menguji keamanan sistem Anda, maka Anda tidak dapat menyalahkan siapa pun selain diri Anda sendiri.
Terakhir: Saya bukan seorang cryptographer. Apa pun yang saya katakan adalah pendapat saya, tetapi kebetulan saya pikir itu didasarkan pada akal sehat ... dan banyak membaca. Ingat, jadilah paranoid mungkin, buat hal-hal sesulit mungkin untuk mengganggu, dan kemudian, jika Anda masih khawatir, hubungi peretas topi putih atau kriptografi untuk melihat apa yang mereka katakan tentang kode / sistem Anda.