gpt4 book ai didi

c# - 如何防止 .NET 中的 DLL 欺骗

转载 作者:行者123 更新时间:2023-12-02 04:22:12 24 4
gpt4 key购买 nike

我有一个引用托管 DLL 的 .NET 应用程序。

这个 DLL 包含一个类,比如 ScoreKeeper实现了一个名为 GetHighScore() 的方法.应用程序会定期调用它。

有没有办法阻止 .NET 应用程序在此处使用“非授权”DLL 代替我提供的 DLL?

最佳答案

你提到:

This DLL contains a class, say ScoreKeeper that implements a method called GetHighScore(). The application calls this periodically.



进而:

Is there a way to prevent the .NET application from using a "non-authorized" DLL here in place of the one I am supplying?



假设您想阻止某人用自己的具有相同名称和类型(在同一命名空间中)的程序集换出您提供的程序集,您可以 apply a strong name to the assembly包含 ScoreKeeper类并让您的消费者引用。

但是,我们会看到有些问题使这不是 100% 可靠。强名称可帮助您保护不知情的用户免于用恶意的欺骗副本替换您的 DLL。但是如果用户是欺骗的同谋(如果他试图作弊就是这种情况),那么代码签名将只不过是一个减速带,并没有提供真正的保护。当然,强名称不能提供与例如类似的保护。朋克克星。

使用强名称验证程序集发布者的身份

当您向程序集添加强名称时,您将使用私钥(非对称公钥/私钥对的一部分,稍后将详细介绍)生成加密哈希,并且公钥包含在程序集名称中(与哈希)。

使用公共(public)散列和公共(public) key ,CLR 能够验证程序集的签名确实来自私有(private) key 。

当然,这意味着,您应该保护 key (内部和外部);如果其他人拥有您的 key ,那么他们可以有效地冒充您并发布人们认为来自您的程序集。

然后,当您添加对已签名程序集的引用时,如果有人试图将具有相同程序集名称(不是完全限定的名称,只是没有版本、哈希和公钥的名称)和相同类型名称的不同程序集放入,尝试加载类型时CLR填充失败,说明找不到;使用完全限定的程序集名称以及命名空间和类型名称解析类型。

为什么强名称不是 100% 安全的(有什么问题吗?)

1) 哈希冲突

它仍然是一个正在验证的哈希。虽然散列非常大(默认散列算法 SHA-1 为 160 位),但任何具有有限数量值的散列都会发生冲突。虽然极不可能,但有可能(不可能与不可能)。此外,默认情况下仅使用最后 8 个字节。结合研究表明 SHA-1 相对较弱,这是使用 SHA-256 增强强命名的一个很好的理由,如 MSDN 中所述。 .

2) 删除强名称

可以删除强名称。但是,在这种情况下,因为您的程序集是 referencing the strong named version of the referenced assembly ,当您的程序集尝试使用受损版本时,它会在运行时失败,假设您已正确重新启用验证(见下文)。

3) 对程序集的物理访问意味着所有程序集

如果有人可以访问物理机器并且可以修改您引用的程序集,那么您的程序集同样容易受到攻击。如果攻击者有能力修改您引用的程序集的强名称,那么他们也可以轻松修改 您的集会和所有其他参与执行的人 .为此, the only way to be 100% sure that the physical assembly isn't hacked is to deny physical access through it .当然,这会带来一系列不同的安全问题。

4) 管理员禁用强名称检查

计算机管理员可以简单地绕过强名称检查,使用 sn -Vr .根据 MSDN :

Registers assembly for verification skipping... A malicious assembly could use the fully specified assembly name (assembly name, version, culture, and public key token) of the assembly added to the skip verification list to fake its identity. This would allow the malicious assembly to also skip verification.



5) .NET 3.5 SP 1 后必须显式启用强名称检查

从 .NET 3.5 SP 1 开始, simply having a strong name doesn't provide any protection :

Starting with the .NET Framework version 3.5 Service Pack 1 (SP1), strong-name signatures are not validated when an assembly is loaded into a full-trust AppDomain object, such as the default AppDomain for the MyComputer zone.



为了让 .NET 检查加载到应用程序中的每个程序集的强名称,您需要将以下代码段(由 MSDN 提供)插入到应用程序配置文件中:

<configuration>
<runtime>
<bypassTrustedAppStrongNames enabled="false" />
</runtime>
</configuration>


但是请注意,这只能防止强名称被删除。

When you override the bypass feature, the strong name is validated only for correctness; it is not checked for a StrongNameIdentityPermission. If you want to confirm a specific strong name, you have to perform that check separately.



如果考虑到上述问题,您仍然希望对程序集进行强命名,方法如下。

生成强名称并签署您的程序集

在生成强名称时,您有两个选择使用哪个键。在 Visual Studio 中,转到项目属性上的 Signing 选项卡,然后单击“Sign the assembly”:

"Sign the assembly" option on the "Signing" tab of the project properties in VS.NET

从那里,您有两种选择来生成公钥/私钥,让 VS.NET 为您生成 key ,或者指向现有的 key :

"New" or "Browse" options for choosing a strong name key file

选择“新建”时,Visual Studio 将提示您输入要生成的文件的名称,以及是否要选择使用密码来访问它:

Create strong name key dialog

此时, key 将添加到您的项目中:

Key added to project

现在,您可以将其移至解决方案项(如果您的解决方案中有多个项目)。

在这种情况下,Visual Studio 实际上只是调用 Strong Name command line tool生成公钥和私钥对。如果您更愿意自己做,请调用 sn.exe-k生成 key 的命令行选项,如下所示:
sn -k keyPair.snk

然后通过上面的“浏览”对话框添加它。

请注意,当您执行此操作时,它会将 key 拉入您的项目。如果您不想这样做(因为它会将 key 复制到每个项目中),请从项目中删除 key ,然后 add an existing file to the project, but link it .这将清除“选择强名称 key 文件”选项,但如果将其下拉,您将看到链接的 key 文件的完整路径。

关于c# - 如何防止 .NET 中的 DLL 欺骗,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13346265/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com