.NET中如何安全地存储认证信息(C#)
TODO: 本文由 赤石俊哉 翻译整理,您可以将本文自由地用于学习交流。如需用于其他用途请征得作者的同意。
原文链接:
验证输入的用户名和密码
如果你只希望验证输入的用户名和密码是否匹配,可以使用Rfc2898DerivedBytes
类(即PBKDF2
)。这比起使用诸如三次DES以及AES这样的加密算法来说要更安全一些,因为从RFC2898DerivedBytes
产生的结果逆推出密码原文是不可行的。你只能将密码转换成PBKDF2
的结果。
存储密码
如果你希望存储密码以便以后进行复用,你可以使用。
它是使用了操作系统生成并且保护的密钥进行三次DES加密算法来加密解密信息的。这就意味着你的应用程序可以省去一个大麻烦,那就是它不需要去关心密钥如何去生成以及保护。在C#
中,使用System.Security.Cryptography.ProtectedData
类。
ProtectedData.Protect()
加密一小段数据: // 需要被保护的数据。使用Encoding.UTF8.GetBytes()将一个字符串转换成byte数组。byte[] plaintext;// 生成一个附加的熵(用于向量的初始化)byte[] entropy = new byte[20];using(RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider()){ rng.GetBytes(entropy);}byte[] ciphertext = ProtectedData.Protect(plaintext, entropy, DataProtectionScope.CurrentUser);
安全地存储熵值(entropy
)和加密后文本(ciphertext
),比如存储在一个只有当前用户具有读写权限的文件或者注册表项内。
ProtectedData.Unprotect()
: byte[] plaintext = ProtectedData.Unprotect(ciphertext, entropy, DataProtectionScope.CurrentUser);
还有一些其他要注意的安全考虑,比如,避免直接将像密码这类的隐私信息存储为一个字符串(string
),这样做的话在内存中是不可被通知的,所以其他人要是查看程序的内存或者Dump内存的时候,就会看到密码。
SecureString
或者一个byte数组来代替。在不需要使用密码的时候,尽快释放掉他们,或者是全部填写0。