当使用P/Invoke时,.NET 4方法安全性异常

9
我有一些代码使用pinvoke调用本地win32。自从我升级到.NET 4后,这段代码开始抛出MethodAccessException异常,显示:
“Tek.Audio.Midi.MidiDevice.GetDevices()”方法的安全透明性尝试通过“Tek.Native.Windows.Multimedia.midiInGetNumDevs()”方法调用本机代码失败。必须是安全关键或安全安全关键的方法才能调用本机代码。
以下是发生的情况:
可执行程序集的Program.Main方法调用library1公共静态Tet.Audio.Midi.MidiDevice.GetDevices()。
Library1的GetDevices()调用library2的public static pinvoke Tek.Native.Windows.Multimedia.midiInGetNumDevs()(是的,不好的做法,但不管怎样)。
涉及的类、方法和程序集上唯一与安全相关的属性是library1上的AllowPartiallyTrustedCallers,而我甚至不知道为什么会这样。
我很惭愧地承认,我对.NET中的安全性相当无知。我该怎么做才能防止这个异常?还有,在这里,有什么好的文章可以让我开始了解.NET安全性吗?
1个回答

16

你有选择余地。最简单的方法是“退出”新的安全模型。


<configuration>
  <runtime>
    <NetFx40_LegacySecurityPolicy enabled="true" />
  </runtime>
</configuration>

鉴于我不是 .Net 4 安全专家,所以 OR(请注意)

编辑:选择退出 .Net 4 安全模型并不可靠,应该避免使用

您可以标记您的方法:

[SecuritySafeCritical]

因为你可以将其与为部分受信任的调用者设计的代码一起使用。

不幸的是,我没有一篇好的文章可以发送给你,我不得不像你一样通过修复我的破碎的代码来解决这个问题。 :)


这个属性起到了作用。在有人能够给出更详细的解释或解释为什么需要它,它是如何工作以及其后果是什么的链接之前,我将接受这个答案。 - Trillian
1
我可以告诉你为什么需要它。Interop是一个“完全信任”的操作,这意味着我们的应用程序必须被完全信任才能执行它。因此,我们需要向运行时发出信号,表明我们的代码希望被清除以执行完全信任操作。通过使用SecuritySafeCritical标记,我们指示即将调用的方法将需要完全信任,并且对于部分受信任的调用者是安全的,也就是说,没有满足完全信任条件或者只是在部分信任下运行的代码(ASP.NET Web应用程序通常在共享托管系统中以部分信任方式运行)。 - Nick Daniels
“标记你的方法”是指GetDevices()吗?还是midiInGetNumDevs()?还是两者都是?我不太清楚。 - Jeffrey LeCours
你是否有更全局的解决方案,而不是将其添加到每个类和函数中? - Kraang Prime
不。你以前可以完全选择退出。现在,就不太行了。 - Nick Daniels
显示剩余3条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接