2011-01-25 44 views
4

打開'portable_hashes'。 我注意到,無論出於何種原因,它生成的哈希值並不總是一樣的 - 但是,當通過「CheckPassword」傳遞總是返回爲有效。我也注意到'PHP_VERSION'用於散列的生成 - 這兩件事結合在一起讓我擔心......便攜式便攜性如何?我可以在服務器,linux,windows,64位,32位等之間移動哈希值(保存在用戶數據庫中) - 並且仍然驗證它們嗎?爲了使密碼不再被驗證,我需要做些什麼?在幾臺服務器之間使用phpass有多安全?

我問的原因是因爲我在我的框架中使用phpass來爲我的幾個網站提供密碼,其中許多網站目前有幾千個用戶 - 而且有些情況下我必須移動他們到不同的服務器上,當然還有升級php。我也可以將其中的一個或兩個從Apache切換到例如lighthttpd或類似的東西。不用說,我非常偏執,我將有一天會有一個支持噩夢,我將無法以任何其他方式修復它,而不是將新密碼發送給每個人(這聽起來確實不安全)。

如果有哪怕是一丁點的機會,密碼將永遠進行的無效 - 我會採取什麼步驟使自己的密碼哈希生成?我已經使用了一個16字節的隨機鹽(每個用戶),除此之外唯一的問題就是延伸 - 對嗎?

回答

8

根據不同的PHP版本,你不需要對便攜式哈希值。在PHP 5.3及以上版本中,如果PHP在系統上不可用,PHP提供自己的bcrypt實現。 如果你所有的服務器都有PHP 5.3及以上版本,我強烈建議關閉便攜式哈希。 PHPass「portables hashes」存在,因爲根據安裝的PHP版本,bcrypt可能不可用。

這就是說,PHPass便攜式哈希不存儲在其散列鹽。這就是爲什麼每次運行相同的密碼是不同的。

此外,PHPass這些哈希*檢查是否可用該版本的md5()功能支持$rawMode參數的生成過程中使用PHP_VERSION。如果沒有,pack()是用十六進制數據轉換成二進制(注意,這是相當慢的那麼簡單的使用$rawMode,這就是爲什麼分支由)。

再次,如果所有服務器正在運行PHP 5.3及以上版本,我強烈建議關閉便攜模式,讓PHPass使用bcrypt代替。由於PHP 5.3+在系統不可用時提供了自己的實現,因此您的散列可以跨操作系統進行檢查。即使你關閉了便攜模式,PHPass仍然會足夠聰明,以正確的方式檢查你的舊哈希。

我和你的情況一樣,在我的框架中跨多個站點使用PHPass。由於我關閉了便攜模式,因此我已將登錄腳本設置爲逐漸重新散列未在登錄時使用bcrypt的密碼。

* 131線


編輯:更多解釋,這裏是在便攜方式哈希值是如何產生的(簡化,並沒有使用PHPass發現實際變量,但準確)。請注意,PHPass使用他們自己的base64編碼版本。

  1. $final = '$P$'

  2. $final .= encode64_int($rounds)(從構造,最小值是5上PHP 5+,其他3個)

  3. $final .= genSalt()(鹽是6個字節在... 8個字節 「encode64」 格式)。

  4. $hash = md5($salt . $password)

  5. 對於2$rounds次,做$hash = md5($hash . $password)

  6. $final = encode64($hash)

所以最終的哈希本質上是這樣的:

$P$9IQRaTwmfeRo7ud9Fh4E2PdI0S3r.L0 
\__________/\____________________/ 
    \     \ 
    \     \ Actual Hash 
    \ 
    \ $P$ 9 IQRaTwmf 
     \_/ \ \______/ 
     \  \  \ 
      \  \  \ Salt 
      \  \ 
      \  \ # Rounds (not decimal representation, 9 is actually 11) 
      \ 
       \ Hash Header 
1

,我可以看到的PHP_VERSION的唯一用途是在這一行:

$output .= $this->itoa64[min($this->iteration_count_log2 + 
    ((PHP_VERSION >= '5') ? 5 : 3), 30)]; 

現在,所有這一切說是確定迭代的最大數量。它在產生鹽的gensalt_private方法中。所以這隻會在存儲新密碼和生成鹽時纔會發生。因此,所有以前生成的鹽都是100%便攜式的。所以根本就沒有真正的可移植性問題...

至於其他方面,只要您使用的是最新版本的PHP(5.0+),就不應該有任何可移植性問題所有的,據我可以告訴(因爲hash功能是內置的)...

+0

謝謝,但鹽不會存儲在任何地方 - 根據我的理解,它會在每次散列時根據設置生成鹽分,或根據現有散列進行檢查。我知道我沒有存儲任何東西,除了產生的哈希之外,我的鹽是我自己創造的。 知道了,有沒有問題切換版本?就好像它在一臺裝有PHP 4的服務器上,並且它們升級到5.或者任何其他可能導致哈希值不一致的問題。 說起來 - 每次運行它時它是如何爲相同的密碼生成一個新的散列?那部分也讓我感到困惑。 – Jon 2011-01-25 02:22:32

+0

@Jon你確定它沒有在散列密碼中存儲鹽嗎?是否有存儲它的輸出或部分輸出?我通常使用像我提交給Kohana的自定義方法:[補丁文件](http://dev.kohanaframework.org/attachments/1495/kohana_security_patch.patch)。唯一可能需要更改的是默認的散列方法,並且`makeSaltedHash`中的回合數量從20到500(或更高的數字)... – ircmaxell 2011-01-25 02:29:31

相關問題