对于网络应用程序,我想创建一个简单但有效的许可系统。在 C# 中,这有点困难,因为任何安装了 Reflector 的人都可以查看我的解密方法。
在 C# 中加密文件的一些方法有哪些是相当防篡改的?
最佳答案
听起来您想使用公共(public)/私有(private)加密来签署许可证 token (例如 XML 片段或文件),以便检测篡改。处理它的最简单方法是执行以下步骤:
1) 为您的公司生成 key 对。您可以使用 SN 工具在 Visual Studio 命令行中执行此操作。语法是:
sn -k c:\keypair.snk
2) 使用 key 对强命名(即签名)您的客户端应用程序。您可以使用应用程序属性页面中的签名选项卡进行设置
3) 为您的客户创建一个许可证,这应该是一个 XML 文档并使用您的私钥对其进行签名。这涉及简单地计算数字签名和完成它的步骤可以在以下位置找到:
http://msdn.microsoft.com/en-us/library/ms229745.aspx
4) 在客户端检查许可证时,您加载 XmlDocument 并使用您的公钥验证签名以证明许可证未被篡改。有关如何执行此操作的详细信息,请访问:
http://msdn.microsoft.com/en-us/library/ms229950.aspx
要绕过 key 分发(即确保您的客户端使用正确的公钥),您实际上可以从已签名的程序集本身中提取公钥。从而确保您没有另一个 key 可以分发,即使有人篡改程序集,.net 框架也会因安全异常而终止,因为强名称将不再与程序集本身匹配。
要从客户端程序集中提取公钥,您需要使用类似于以下的代码:
/// <summary>
/// Retrieves an RSA public key from a signed assembly
/// </summary>
/// <param name="assembly">Signed assembly to retrieve the key from</param>
/// <returns>RSA Crypto Service Provider initialised with the key from the assembly</returns>
public static RSACryptoServiceProvider GetPublicKeyFromAssembly(Assembly assembly)
{
if (assembly == null)
throw new ArgumentNullException("assembly", "Assembly may not be null");
byte[] pubkey = assembly.GetName().GetPublicKey();
if (pubkey.Length == 0)
throw new ArgumentException("No public key in assembly.");
RSAParameters rsaParams = EncryptionUtils.GetRSAParameters(pubkey);
RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
rsa.ImportParameters(rsaParams);
return rsa;
}
我已经在 Snipt 上上传了一个示例类,其中包含很多有用的加密实用程序:http://snipt.net/Wolfwyrd/encryption-utilities/帮助您顺利上路。
我还在以下网址提供了一个示例程序:https://snipt.net/Wolfwyrd/sign-and-verify-example/ .该示例要求您将其添加到具有加密实用程序库的解决方案中,并提供测试 XML 文件和用于签名的 SNK 文件。该项目应设置为使用您生成的 SNK 进行签名。它演示了如何使用来自 SNK 的私钥对测试 XML 文件进行签名,然后使用程序集上的公钥进行验证。
更新
添加了一个 up to date blog post对许可证文件进行了详细的介绍
关于c# - 加密许可证文件的有效方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/359342/