來自數字 PIN 的加密密鑰派生?
我想在 Android 應用程序中儲存加密的數據。在應用程序之外保持加密密鑰的安全不是一種選擇,因此我研究了密碼派生密鑰算法。
我在博文“ Android 開發者——使用密碼學安全地儲存憑證”中找到了一個來自 Android 的好例子。讓我引用重要的程式碼:
public static SecretKey generateKey(char[] passphraseOrPin, byte[] salt) throws NoSuchAlgorithmException, InvalidKeySpecException { // Number of PBKDF2 hardening rounds to use. Larger values increase // computation time. You should select a value that causes computation // to take >100ms. final int iterations = 1000; // Generate a 256-bit key final int outputKeyLength = 256; SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1"); KeySpec keySpec = new PBEKeySpec(passphraseOrPin, salt, iterations, outputKeyLength); SecretKey secretKey = secretKeyFactory.generateSecret(keySpec); return secretKey; }
這種方法似乎暗示使用 PIN 進行密鑰派生是一種很好的做法。
用蠻力是不是太容易了?
在其他 PIN 應用程序中,有一個外部系統限制嘗試次數,從而使這種方法安全。但是,在此應用程序中,我看不到 PIN 是如何安全的。
在受感染的系統上,使用者擁有加密數據,並從應用程序/程式碼中知道該 pin 是 $ n $ 數字。所以他可以蠻力每 $ 10^n $ 可能性並使用加密數據來查看使用該派生密鑰/pin 組合進行解密是否返回任何有效數據。
說明密碼密鑰派生需要字母數字密碼才能安全是否正確
編輯:
一般來說,我理解字母數字密碼比數字密碼好。我對我的理論的回饋很感興趣,因為除了那個 pin 之外的所有數據都儲存在移動設備上,因此我可以更容易地暴力破解 pin。
我也在尋找替代品。知道我們只有一個密碼作為使用者的秘密輸入,有沒有辦法讓這個安全?
攻擊者通常擁有至少與生成密鑰的人一樣快的平台。因此,蠻力攻擊者可以在 1000 秒或 17 分鐘內測試所有 4 位 PIN(基於問題中提到的 100 毫秒秒)。
順便說一句,使用大於至少 1000 次或更長時間的迭代計數是相當普遍的(就像任何需要 1 秒來處理的事情。在現代平台上,10000 或 100000 的計數可能是完全合理的)。此外,通常會通過延遲懲罰錯誤嘗試來減慢猜測速度。
如果攻擊者能夠訪問某些計算能力,例如為破解 PBKDF2 而設計的 ASIC 電路,他們可能能夠以快 1000 倍的速度破解秘密,即每秒可以猜測 10000 個引腳/密碼(假設密鑰派生需要設備上 100 毫秒秒)。
–
為了使 PIN 和 PBKDF2 免受攻擊,通常必須執行以下操作:
- 攻擊者無法直接訪問設備上的儲存(以獲取使用專用設備離線破解秘密所需的值)
- 該設備不允許非常快速地嘗試許多 PIN(嘗試後增加延遲)。
- 失敗嘗試次數過多會鎖定設備。
但是,通常使用良好的密碼比使用 PIN 碼安全得多。 這是我之前關於 PIN 或密碼安全性的回答,當攻擊者可以使用暴力破解所需的材料時。