如何設計具有數據共享能力和密碼重置的密碼系統
我最初在 security.stackexchange 論壇上發布了這個,但後來我被引導到這個似乎更適合我的問題的那個。
我正在編寫一個 C# .NET 應用程序。對於我的應用程序,應滿足以下要求:
- 使用者的數據應加密儲存在數據庫中
- 使用者可以與其他使用者共享數據
- 我,作為開發者,應該無法解密任何使用者數據
- 如果使用者重置密碼,之前加密的數據應該仍然可以解密
- 私鑰不應儲存在磁碟上的任何位置。理想情況下,我希望客戶端應用程序能夠在每次使用者登錄時從密碼中獲取私鑰。
我似乎找不到滿足所有五個要求的解決方案。到目前為止,我已經提出了以下使用非對稱加密的密碼系統:當使用者註冊時,根據使用者密碼派生一個公私密鑰對(這甚至可能/實用嗎?)。公鑰儲存在數據庫中。當使用者與另一個使用者共享數據時,它會使用該使用者的公鑰加密並儲存在數據庫中。但現在要求。不滿足 4,因為密鑰對基於目前密碼,重置將使所有先前加密的數據無法解密。
相反,如果我使用對稱加密來加密數據,那麼我可以使用一些基於密碼的密鑰來加密加密密鑰,從而解決 req. 4. 但是,我無法滿足要求。2 即與其他使用者共享數據。當然,這是因為使用者需要使用私鑰加密的其他使用者的對稱數據加密密鑰。
因此,我發現自己陷入困境,無法提出同時解決所有問題的解決方案。
片語“密碼重置”不適用於加密。
密碼重置意味著從某個時刻開始,只能使用新密碼,並且不能再使用以前的密碼。對於加密,這是不可能的,因為如果某些密碼(密鑰)可以用於解密,它仍然可以不受任何限制地使用。例如,如果可以重置並且使用者將密碼重置為新密碼,那麼幾天后找到之前的密碼,這個密碼顯然仍然能夠解密相同的數據。
因此,我們不能將其稱為“重置”。在使用者忘記密碼的情況下能夠解密數據的要求實際上意味著:
- 您可以幫助使用者恢復目前密碼(解密密鑰)
- 或者,如果加密方案允許多個解密密鑰,則為使用者提供額外的密碼(密鑰)
在這兩種情況下,作為開發人員,您不僅可以在使用者詢問此問題時獲得密碼(解密密鑰),還可以自行獲得密碼(解密密鑰)。因此,將違反要求 3。
任何具有秘密共享的方案也不符合這些要求。如果您在使用者擁有一部分附加解密密鑰的情況下實施秘密共享,這也可能會失去。如果您在使用者沒有共享秘密的任何部分的情況下實施秘密共享,則可以在使用者不知道的情況下恢復秘密(解密密鑰),因此將違反要求 3。
簡而言之:沒有辦法同時滿足您的所有要求。這與密碼學無關,這只是常識。意味著,至少需要更改一項要求。
如果我們假設使用者在失去密碼時會失去所有機密,則要求 3+4 意味著 3 的開發人員不能像 4 中那樣更改使用者密碼。此外,任何加密或解密數據的程式碼都可以明文操作它,並且任何密鑰是需要的。
3 的開發者因此必須無法惡意編寫或更改負責使用者管理的程式碼。而如果3的開發者可以惡意編寫或篡改負責加密或解密的程式碼,那麼該開發者一定不可能使該程式碼洩漏數據(包括解密密鑰,以及明文或密鑰下加密的明文數據)由上述開發商所知)。
因此 3 的開發者編寫的任何 C# 程式碼必須至少匹配以下之一
- 它由獨立於開發人員的受信任方審核和執行。
- 它不負責使用者管理和數據加密,也不能改變其他受信任程式碼的性質或行為。如果其他受信任的程式碼是同一程序的一部分,這在C# 中很難保證(其他語言如 Java 在這方面提供了更多的保證)。
- 對於負責加密或解密的程式碼,它產生的東西在某種程度上對開發人員來說是不可用的,或者經過交叉檢查以使洩漏不可能。最簡單的(因此是高安全性環境中的最佳和最佳實踐)是在受信任的邊界中執行開發人員的程式碼,其中產生的資訊無法到達開發人員。嘗試通過物理隔離機器、虛擬機、VPN 和數據二極體來確保沒有資訊可以從 IT 系統流向開發人員¹。
因此,我發現自己陷入困境,無法提出同時解決所有問題的解決方案。
是的。歡迎來到 IT 中實踐的密碼學所允許的現實:至少必須信任系統的核心部分。
¹發布程式碼後開發者謀殺解決了 3,但無法有效防止數據洩露給他人,並且在某些司法管轄區是非法的。此外,雖然當您詢問不幸的使用者時它通常是完全合理的,但它仍然不受開發人員的歡迎。