[英]openssl_digest vs hash vs hash_hmac? Difference between SALT & HMAC?
我想使用SHA512來存儲密碼。 要做到這openssl_digest
,我應該使用openssl_digest
, hash
和hash_hmac
哪一個?為什么?
SALT
和HMAC
什么區別?
我剛剛讀到HMAC是建立在哈希函數之上的。
SHA512+SALT+HMAC
真的有必要還是SHA512+SALT
或SHA512+HMAC
?
所以,首先,讓我們清楚一件事。 openssl_digest()
=== hash()
。 它只是另一個不同名稱的功能,完全相同。 它計算輸入的加密哈希值。
所以,現在我們有了一個問題: 存儲密碼時哪個更好: hash
或hash_hmac
?
也不
事實證明, 彩虹表已經死了 。 只使用hash($password . $salt)
甚至hash_hmac($password, $salt)
對於密碼存儲來說還不夠好。 期。 如果您這樣做,請立即停止。
原因很簡單:計算機(或GPU)上的計算時間非常便宜。 這是如此便宜,以至於蠻力的密碼列表足夠便宜,你需要擔心它。 請記住,哈希函數設計得很快 。 不貴啊...
但是,事實證明,有一種方法可以使這些快速哈希函數更加昂貴。 事實上,它非常簡單:迭代。
現在,我知道你在想什么。 你將只是循環哈希:
function hash_password($password, $salt) {
$hash = hash("sha512", $password . $salt);
for ($i = 0; $i < 1000; $i++) {
$hash = hash("sha512", $hash);
}
}
當然這很好,對吧? 不。 正如Hashing和Encryption之間的基本差異所解釋的那樣,這不是一個好主意。 那么為什么不再重新輸入密碼和鹽呢?
function hash_password($password, $salt) {
$hash = hash("md5", $salt . $password);
for ($i = 0; $i < 1000; $i++) {
$hash = hash("md5", $hash . $password);
}
}
事實上,這正是PHPASS使用的(略微調整,但這是基本算法)...
所以現在1調用hash_password
執行1000個哈希循環。
但我們可以改進嗎?
好吧,事實證明,我們可以。 下一個合乎邏輯的做法是看看我們是否可以在相同的時間內獲得更多的哈希循環。 這就是hash_hmac()
用武之地。事實證明, HMAC
每次調用時都會使用2個哈希周期。 而且因為它都是C,所以它只需要hash()
執行一輪的時間量的1.5倍。
這意味着如果我們用hash_hmac
替換hash
,我們可以立即看到在指定時間內完成的工作量增加了33%。 所以現在我們在這里:
function hash_password($password, $salt) {
$hash = hash_hmac("md5", $salt, $password);
for ($i = 0; $i < 1000; $i++) {
$hash = hash_hmac("md5", $hash, $password);
}
}
這實際上是PBKDF2的基本內循環。
但我們可以變得更好嗎?
是的,再次,我們可以變得更好。 如果我們仔細觀察,我們可以看到 - 除了密碼和鹽 - 所有上述算法都使用非常少量的內存。 在sha512的情況下,它們將使用128到256字節(緩沖區和狀態)的順序來散列密碼。 由於內存使用量非常小,因此在GPU中並排運行大量內存非常簡單。 如果我們只能增加內存使用量......
好吧,事實證明,我們可以簡單地使用bcrypt
,這是一種自適應散列算法。 它的優點是它使用比上述算法更多的內存(大約4到5kb)。 因此,對並行化更具抵抗力。 並且由於它的計算成本很高,因此它對強制執行是不利的。
幸運的是,它適用於PHP:
crypt($password, '$2y$07$usesomesillystringforsalt$')
請注意, crypt()
使用許多算法,但$2y$
和$2a$
算法是bcrypt
。
但我們能改進嗎?
的種類。 有一種叫做scrypt的相對較新的算法。 它比bcrypt更好,因為它的計算成本非常高,但是使用了更多的內存(大約20mb到40mb來散列單個密碼)。 因此,對並行化更具抵抗力......
不幸的是,PHP中還沒有 scrypt
(我正在努力改變它)。 在那之前,使用bcrypt
......
在LinkedIn , LastFM , Hotmail , Gawker等最近的經驗教訓之后,很明顯很多人都做錯了。 不要做錯,使用帶有審查算法的庫。 使用CRYPT_BLOWFISH
(bcrypt),使用PHPASS,使用PasswordLib 。 但是不要僅僅因為你不想依賴而發明自己的......這只是疏忽。
更多閱讀:
HMAC是使用哈希算法(如SHA512)的特定方法。 它用於簽署消息,然后您可以驗證消息是否來自特定簽名者並且未被更改。 所以這不是你想要的。
salt用於向應加密或散列的文本添加一些“隨機性”。 關鍵是,即使您多次加密相同的文本,您也會得到不同的結果。 這使得進行一些攻擊變得更加困難。 這就是你想要的: SHA512(salt+password)
。
對於存儲密碼,我能想象的最安全的方式是:
(免責聲明:我對加密技術不是很熟悉,可能有更好的解決方案)
要驗證密碼,您需要執行以下操作:
當然,你可以用明文傳輸密碼並在服務器上進行整個salting和散列,但這會大大削弱你的解決方案。 您絕不應以明文形式傳輸密碼。
但是“將鹽傳遞給客戶”部分可能是個問題。 我可以想象解決這個問題的一種方法是以某種方式從用戶名中獲取salt(最簡單的方法:只做lowercase(username) + password
),但問題是鹽可以預測,從而削弱你的解決方案一點點。 然而,它仍然方式比發射“原始”哈希更好,你甚至不會需要存儲的鹽,你可以從用戶名,每次得到它。 如果您的密碼數據庫被盜,它仍然可以通過這種“用戶名腌制”方法抵御彩虹表攻擊。
問題是仍然可能發生中間人攻擊。 如果攻擊者攔截用戶名和哈希,則它具有所有相關的信息,並且與發送明文密碼沒有任何不同。 因此,您可能希望使用SSL(HTTPS)保護連接。
根據IT安全專家的說法:
使用Bcrypt來源: https : //security.stackexchange.com/a/10905/7599 。
我會根據SO的觀點給出答案。
openssl_digest vs hash vs hash_hmac
並且在密碼學中, 基於散列的消息認證碼(HMAC)是用於計算涉及密碼散列函數結合密鑰的消息認證碼(MAC)的特定結構。
正如ircmaxell所說, hash
或hash_hmac
對於使用SHA-512存儲密碼並不是更好。 我寧願說,您可以使用openssl_digest
存儲密碼。
SALT vs HMAC
HMAC旨在用於您擁有隨機密鑰的情況。 對於這些情況,HMAC通常比將密鑰合並到散列函數中的其他方式更好。 (例如,使用HMAC處理擴展攻擊等事情)
鹽通常是一個非秘密的隨機值。 也就是說,當你使用術語salt時,通常指的是攻擊者可能已經知道隨機值的情況。 因此,系統的安全性不應取決於保密的鹽。 在這些情況下,HMAC通常不是一個很好的選擇。
HMAC和Salt比較不合邏輯。 就個人而言,我會使用一個salt和一個哈希函數......我不會對哈希函數的強弱感到偏執,因為它不太可能成為任何實際系統中的薄弱環節....
請參閱http://www.derkeiler.com/Newsgroups/sci.crypt/2006-01/msg00321.html
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.