在.NET中存储encryption密钥的最佳方法C#

在我们的应用程序中,我们有很多敏感的configuration设置,我们将其存储在一个xml文件中,这个文件又被encryption了。

这个安全的文件必须在运行时被解密并读取configuration值。 但是会出现一个问题,即密钥和初始化vector在代码中是硬编码的,因此任何人都可以使用Reflector读取它。

什么是在.NET中存储encryption密钥的最佳方式,所以没有人可以使用reflection器读取它们?

如果你想保护你的数据从其他用户。 看看ProtectedData类。

(免责声明:保护您的数据,以创build一个复制保护计划不包括在这个答案)。

这些类使用Windows的DPAPI来对用户或机器级别的数据进行encryption和解密。

使用ProtectedData / DPAPI可以使您免于处理密钥并自行保护数据。 您可以select保护当前用户的数据。 数据可以从不同的计算机,由相同的域用户读取。

如果你想创build自己的密钥。 您可以为每个用户/机器创build一个密钥,并将该密钥存储在registry中。 由于registry可以被保护,只有当前用户可以读回密钥。 我知道registry有不良的业力,但实际上非常擅长存储这样的数据。

PS:不要把你的代码中的IV。 每次创build一个新的IV,并把它放在数据的前面。

如果你不能用reflection器阅读它们,你期望程序如何阅读它们? 您可以将它们分解并存储到整个地方,但是(AFAIK)一旦您需要您的程序能够读取它们,则可以对其进行混淆,那么任何有权访问您的代码的人都可以阅读它们。

不要忘记内存中的值也可以被访问( 咳嗽 SecureString)。

你应该使用机器密钥库,这是一个安全的存储,特别是为了这个目的。 例如:

CspParameters cspParams = new CspParameters(PROV_RSA_FULL, null, KEYNAME); cspParams.Flags = CspProviderFlags.UseMachineKeyStore; RSACryptoServiceProvider rsa = new RSACryptoServiceProvider(cspParams); 

其中KEYNAME是一个自定义string,可以用来稍后检索密钥。

有关更多示例,请参阅此问题: 如何将公钥存储在机器级别的RSA密钥容器中

一般来说,每个会话都要创build一个新的密钥和IV,密钥和IV都不应该存储在后面的会话中使用。

为了将对称密钥和IV传送给远程方,通常使用不对称encryption来encryption对称密钥和IV。 通过不安全的networking发送这些值而不encryption它们是非常不安全的,因为拦截这些值的任何人都可以解密你的数据。 有关encryption和传输密钥和IV的过程的更多信息,请参阅创buildencryptionscheme 。

安装应用程序时,创build一组新的RSA密钥,然后使用私钥作为密码使用AESencryption数据。 由于Windows将RSA私钥安全地存储在创build它们的PC上,数据只能由创build数据的计算机解密,因为只有该计算机才具有必要的密钥。

将文件encryption/解密密钥存储在远程服务器上,通过https服务将它传递给应用程序? 这种方式的关键留在电脑的内存中,但没有成为一个源代码文件。

这需要通过运行应用程序的人来连接到密钥服务器。

在硬件上存储密钥怎么样,在这里我正在谈论硬件安全模块! 我们可以用它作为最佳实践来隐藏密钥吗? 我们可以将密钥存储在configuration文件中,然后encryptionconfiguration文件? 就我而言,我正在谈论一个独立的.Net应用程序。