确定哪个.NET程序集加载了另一个程序集。

3
我正在订阅AppDomain.AssemblyLoaded事件,并希望了解当前被加载的程序集是从哪个程序集加载而来。
如果程序集A包含对Assembly.Load(AssemblyB)的调用,我想在运行时确定是程序集A导致程序集B被加载。

1
我不相信这是可能的,当程序集被加载时,它会被添加到AppDomain程序集中,而没有保留加载它的程序集的引用。 - Gusman
我不知道它有多可靠,但也许可以使用StackTrace类,并查看在AssemblyLoaded事件发生之前调用堆栈中更高层次的人是谁? - Scott Chamberlain
也许你正在过度复杂化这个问题。如果A以某种方式影响B的位置,那么肯定是你的事件处理程序加载了A。因此,“最后一个”或“之前的”应该有些相关性。不要过度复杂化,DLL地狱很可怕。 - Hans Passant
1个回答

0

这将获取到引用的程序集,这已经相当接近了。我不确定是否可能获得更多细节。

static void Main(string[] args)
{
  AppDomain.CurrentDomain.AssemblyLoad += new AssemblyLoadEventHandler(MyAssemblyLoadEventHandler);
  System.Data.DataColumn d = new System.Data.DataColumn();
  Console.ReadLine();
}
static void MyAssemblyLoadEventHandler(object sender, AssemblyLoadEventArgs args)
{
  Console.WriteLine("ASSEMBLY LOADED: " + args.LoadedAssembly.FullName);
  string loadedAssemblyFullName = args.LoadedAssembly.FullName;
  foreach (System.Reflection.Assembly parent in AppDomain.CurrentDomain.GetAssemblies())
  {
    System.Reflection.AssemblyName[] referencedAssemblies = parent.GetReferencedAssemblies();
    string[] referencedFullNames = (from r in referencedAssemblies select r.FullName).ToArray();
    if (referencedFullNames.Contains(loadedAssemblyFullName))
    {
      Console.WriteLine(System.IO.Path.GetFileName(args.LoadedAssembly.CodeBase) +
                        " was referenced by " +
                        System.IO.Path.GetFileName(parent.CodeBase));
    }
  }
}

输出:

已加载程序集:System.Numerics,Version=4.0.0.0,Culture=neutral,PublicKeyToken=b77a5c561934e089

System.Core.dll 引用了 System.Numerics.dll

System.Data.dll 引用了 System.Numerics.dll

代码来源:https://msdn.microsoft.com/zh-cn/library/system.reflection.assembly.getreferencedassemblies(v=vs.110).aspx

(编辑删除之前无用的回答)


2
该代码只会告诉你是哪个程序集调用了实际的方法,而不是加载了指定程序集的程序集。 - Gusman
编辑以期望真正回答问题,感谢您的建议。 - Dave 5709
再次强调,这个答案是不正确的。它只是说明了哪个程序集引用了哪一个程序集。例如,您创建了一个DLL并引用了mscorlib.dll,在内存中不一定会加载mscorlib,因为它可能已经被加载了... 同样的情况也适用于外部库,假设A、B、C三个库,A引用C,B也引用C,那么A加载C后,B将在外部加载。如果使用您的代码,则会导致A和B都加载了C。 - Gusman
@Gusman - 它不是完美的,但我认为它已经做到了最好。 - Dave 5709

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