2010-11-11 126 views
0

所以我有以下代碼:,一個安全異常

[DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true)] 
    [return: MarshalAs(UnmanagedType.Bool)] 
    static extern bool SetDllDirectory(string dllPath); 

在功能:

  SetDllDirectory(@"G:\Sean\Debug\"); 

      Assembly loadedDLL = Assembly.LoadFrom(@"G:\Sean\Debug\BonderControlPanelSim.dll", AppDomain.CurrentDomain.Evidence); 
      Type rtsObj = loadedDLL.GetType("Oe.Te.Ranorex.Instrument.BonderControlPanelSim"); 
      Object obj = Activator.CreateInstance(rtsObj); 

      rtsObj.InvokeMember("Initialize", BindingFlags.InvokeMethod | BindingFlags.Public | BindingFlags.Instance, null, obj, new object[] { "COM3", 1, 2 }); 
      rtsObj.InvokeMember("PushStart", BindingFlags.InvokeMethod | BindingFlags.Public | BindingFlags.Instance, null, obj, new object[] { 3 }); 
      rtsObj.InvokeMember("Shutdown", BindingFlags.InvokeMethod | BindingFlags.Public | BindingFlags.Instance, null, obj, null); 

然而,當我運行一個小的應用程序從眼前這個功能與DLL相同的文件夾,沒有問題。當我將可執行文件移動到另一臺具有G驅動器映射的計算機時,出現安全異常。

<IPermission class="System.Security.Permissions.SecurityPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" 
version="1" 
Flags="UnmanagedCode"/> 

不知道該如何處理。在Assembly.LoadFrom我通過證據。

在第一個rtsObj.InvokeMember引發異常。

感謝您的幫助!

編輯:應用程序實際上無法在其他機器上啓動。如果我的機器上只有它自己的可執行文件,它將啓動。

回答

1

駐留在遠程網絡共享上的.NET程序集被默認的.NET安全策略認爲不足以讓它們執行P/Invokes。您需要更改安全策略,將程序集複製到本地文件夾(不是映射網絡驅動器),或者完全刪除SetDllDirectory P/Invoke調用。

+0

的PInvoke的是另一個DLL需要在此應用 – 2010-11-11 18:31:44

+1

很好用的多數民衆贊成在一個非託管的組件,如果組件從網絡共享調用,那麼它也將草草收場時,它試圖爲P失敗/ Invoke的。您將**擁有**來更改.NET安全策略,或將程序集複製到機器本地卷以供運行時允許任何* P /調用。 – cdhowie 2010-11-11 18:35:27

1

您可以更改安全策略以允許CLR從遠程源打開。

http://blogs.msdn.com/b/shawnfa/archive/2009/06/08/more-implicit-uses-of-cas-policy-loadfromremotesources.aspx

// From the Article 
// Since this application only trusts a handful of LoadFrom operations, 
// we'll put them all into the same AppDomain which is a simple sandbox 
// with a full trust grant set. The application itself will not enable 
// loadFromRemoteSources, but instead channel all of the trusted loads 
// into this domain. 
PermissionSet trustedLoadFromRemoteSourceGrantSet 
    = new PermissionSet(PermissionState.Unrestricted); 

AppDomainSetup trustedLoadFromRemoteSourcesSetup = new AppDomainSetup(); 
trustedLoadFromRemoteSourcesSetup.ApplicationBase = 
    AppDomain.CurrentDomain.SetupInformation.ApplicationBase; 

AppDomain trustedRemoteLoadDomain = 
    AppDomain.CreateDomain("Trusted LoadFromRemoteSources Domain", 
          null, 
          trustedLoadFromRemoteSourcesSetup, 
          trustedLoadFromRemoteSourcesGrantSet); 

// Now all trusted remote LoadFroms can be done in the trustedRemoteLoadDomain, 
// and communicated with via a MarshalByRefObject. 
+0

我試過這個......它沒有工作。該應用程序甚至不會在其他機器上啓動 – 2010-11-11 18:27:07