请求失败.net程序集

时间:2012-09-24 23:04:11

标签: c# .net

我有一个使用插件的应用程序。装配链看起来像这样:

App - > A - > B - > A - >乙

程序集是“App”(正在运行的应用程序),“A” - 程序集中的链接和“B” - 装载了Assembly.LoadFile或Assembly.LoadFrom的程序集(两种方法都获得相同的错误)

尝试LinkDemand无限制权限时抛出安全异常。当A第二次调用B时会发生异常。 B是 NOT 一个签名的程序集(因此我从我读过的内容中收集到的不是一个强大的命名程序集)。我还尝试在attribute.cs文件中为B添加[assembly:AllowPartiallyTrustedCallers]属性(并尝试将其放在所有程序集上)。我甚至试过为不受限制的权限设置权限断言,但是从我读过的内容来看,它应该对LinkDemand没有任何影响。

我知道程序集已经减少了权限(猜测这与通过程序集加载它有关)。但是,我读过的所有内容似乎都表明LinkDemand只检查调用权限,所以我不确定它为什么会第二次而不是第一次失败。

我很困惑因为:a。为什么不第一次失败,b。为什么会发生这种情况(不使用强大的命名程序集afaik),c。为什么不添加APTC属性修复问题。

为了清楚起见,我没有任何程序集中任何方法的安全需求属性(不包括LinkDemands)。我在程序集A中确实有一些权限断言,但我不知道这会如何影响任何事情。

[System.Security.SecurityException] {"Request failed."} System.Security.SecurityException
Action                              LinkDemand  System.Security.Permissions.SecurityAction
Demanded                            {<PermissionSet class="System.Security.PermissionSet" version="1" Unrestricted="true"/> }   object {System.Security.PermissionSet}
DenySetInstance                     null    object
FailedAssemblyInfo                  {B, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null}  System.Reflection.AssemblyName
FirstPermissionThatFailed           null    System.Security.IPermission
GrantedSet                          "<PermissionSet class=\"System.Security.PermissionSet\"\r\nversion=\"1\">\r\n<IPermission class=\"System.Security.Permissions.FileDialogPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nAccess=\"Open\"/>\r\n<IPermission class=\"System.Security.Permissions.IsolatedStorageFilePermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nAllowed=\"ApplicationIsolationByUser\"\r\nUserQuota=\"512000\"/>\r\n<IPermission class=\"System.Security.Permissions.SecurityPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nFlags=\"Execution\"/>\r\n<IPermission class=\"System.Security.Permissions.UIPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nWindow=\"SafeTopLevelWindows\"\r\nClipboard=\"OwnClipboard\"/>\r\n<IPermission class=\"System.Security.Permissions.UrlIdentityPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nUrl=\"file:///Z:/xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx/B.dll\"/>\r\n<IPermission class=\"System.Security.Permissions.ZoneIdentityPermission, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089\"\r\nversion=\"1\"\r\nZone=\"Internet\"/>\r\n<IPermission class=\"System.Drawing.Printing.PrintingPermission, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a\"\r\nversion=\"1\"\r\nLevel=\"SafePrinting\"/>\r\n</PermissionSet>\r\n" string
Method                              null    System.Reflection.MethodInfo
PermissionState                     "<PermissionSet class=\"System.Security.PermissionSet\"\r\nversion=\"1\"\r\nUnrestricted=\"true\"/>\r\n"    string
PermissionType                      {Name = "PermissionSet" FullName = "System.Security.PermissionSet"} System.Type {System.RuntimeType}
PermitOnlySetInstance               null    object
RefusedSet                          ""  string
Url                                 "file:///Z:/xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx/B.dll"   string
Zone                                Internet    System.Security.SecurityZone

正如Hans Passant所建议的那样,这似乎与安全区是互联网有关。我已经尝试了以下caspol命令无济于事:

caspol -m -ag 1.2 -url file://z:/* FullTrust
caspol -m -ag 1.2 -url file://\\sam-crazycasta.dyndns.org/crazycasta/* FullTrust
caspol -m -ag 1.3 -url file://z:/* FullTrust
caspol -m -ag 1.3 -url file://\\sam-crazycasta.dyndns.org/crazycasta/* FullTrust

但是,复制本地文件确实有效。我想要一个允许我从网络驱动器等运行的通用解决方案。最好我可以在程序中做一些事情,这样用户就不需要知道任何错误。

编辑1:我从MSDN中获取了一些代码来打印出策略,这就是我得到的,看起来像FullTrust应该被授予(最后一行是问题异常):

Policy Level Enterprise:
    FullTrust
    LocalIntranet
    Internet
    SkipVerification
    Execution
    Nothing
    Everything
Policy Level Machine:
    Nothing
    FullTrust
    LocalIntranet
    Internet
    SkipVerification
    Execution
    Everything
Policy Level User:
    FullTrust
    LocalIntranet
    Internet
    SkipVerification
    Execution
    Nothing
    Everything
A first chance exception of type 'System.Security.SecurityException' occurred in mscorlib.dll

此打印输出完全相同,无论是从发生故障的网络运行,还是从运行它的硬盘驱动器运行。

我还尝试添加以下函数并在失败的调用之前调用它:

[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.LinkDemand, Unrestricted = true)]
public void dummy() {}

由于链接要求不受限制的权限,我不明白为什么这个功能有效而另一个没有。

1 个答案:

答案 0 :(得分:0)

我试图杀死程序集B中的进程。这只是部分答案。我仍然感到困惑,因为调试器指向程序集A中的行调用程序集B而不是程序集B中的行,我试图杀死进程。这里有一些代码可以证明这个问题,如果有人可以告诉我,我应该知道异常来自汇编B我是否接受这个答案。

大会A:

using System;
using System.Text;

namespace A
{
    public interface IA
    {
        void A();
        void B();
    }

    public class A
    {
        public IA a;

        public A(IA _a)
        {
            a = _a;
        }

        public void callA()
        {
            Console.WriteLine("callA called, calling A.");
            a.A();
        }

        public void callB()
        {
            Console.WriteLine("callB called, calling B.");
            a.B();
        }
    }
}

大会B:

using System;
using System.Text;

using System.Diagnostics;

namespace B
{
    public class _B : A.IA
    {
        public A.A a;

        public _B(A.A _a)
        {
            a = _a;
        }

        #region IA Members

        public void A()
        {
            Console.WriteLine("A called, calling callB.");
            a.callB();
        }

        public void B()
        {
            Console.WriteLine("B called.");
            Process.GetCurrentProcess().Kill();
        }

        #endregion
    }
}

应用:

using System;
using System.Text;

using System.Reflection;

namespace App
{
    class Program
    {
        static void Main(string[] args)
        {
            A.IA ia;
            Assembly b;
            Type tb;
            A.A a;

            a = new A.A(null);
            b = Assembly.LoadFrom("../../../B/bin/Debug/B.dll");
            tb = b.GetType("B._B");
            ia = (A.IA)tb.GetConstructor(new Type[] { typeof(A.A) }).Invoke(new object[]{a});
            a.a = ia;
            a.callA();
        }
    }
}
相关问题