CLR 如何加载 DLL?

2024-04-14

我的假设始终是 CLR 在应用程序域启动时加载了它所需的所有 DLL。然而,我写了一个例子,让我对这个假设提出质疑。我启动我的应用程序并检查加载了多少模块。

Process[] ObjModulesList;
ProcessModuleCollection ObjModulesOrig;

//Get all modules inside the process
ObjModulesList = Process.GetProcessesByName("MyProcessName");
// Populate the module collection.
ObjModulesOrig = ObjModulesList[0].Modules;

Console.WriteLine(ObjModulesOrig.Count.ToString());

然后我重复完全相同的代码,但我的计数不同。附加的 DLL 是 C:\WINNT\system32\version.dll。

我真的很困惑为什么计数会不同。

有人可以详细说明 CLR 正在做什么以及它如何加载这些东西,以及它是通过什么逻辑这样做的吗?


以下内容抄自Don Box的优秀文章必备.Net。 (可用的here http://my.safaribooksonline.com/0-201-73411-7/ch02lev1sec5#X2ludGVybmFsX0ZsYXNoUmVhZGVyP3htbGlkPTAtMjAxLTczNDExLTcvMjE=)
(恕我直言,这是任何专业 .Net 开发人员必须具备的)

CLR 加载器

CLR 加载器负责加载和初始化程序集、模块、资源和类型。 CLR 加载程序会尽可能少地加载和初始化。与 Win32 加载程序不同,CLR 加载程序不会解析并自动加载从属模块(或程序集)。 相反,只有在实际需要时才按需加载从属部分(与 Visual C++ 6.0 的延迟加载功能一样)。这不仅加快了程序初始化时间,而且减少了正在运行的程序消耗的资源量。 在 CLR 中,加载通常由基于类型的即时 (JIT) 编译器触发。当 JIT 编译器尝试将方法体从 CIL 转换为机器代码时,它需要访问声明类型的类型定义以及类型字段的类型定义。此外,JIT 编译器还需要访问正在 JIT 编译的方法的任何局部变量或参数所使用的类型定义。加载类型意味着加载包含类型定义的程序集和模块。 这种按需加载类型(以及程序集和模块)的策略意味着程序中未使用的部分永远不会进入内存。这还意味着正在运行的应用程序经常会看到随着时间的推移加载新的程序集和模块,因为在执行期间需要这些文件中包含的类型。如果这不是您想要的行为,您有两种选择。一种是简单地声明您想要与加载器显式交互的类型的隐藏静态字段。

加载程序通常会代表您隐式地完成其工作。开发人员可以通过程序集加载器显式地与加载器交互。程序集加载器通过以下方式向开发人员公开LoadFrom上的静态方法System.Reflection.Assembly班级。此方法接受 CODEBASE 字符串,该字符串可以是文件系统路径,也可以是标识包含程序集清单的模块的统一资源定位符 (URL)。如果找不到指定的文件,加载器将抛出一个错误System.FileNotFoundException例外。如果可以找到指定的文件,但不是包含程序集清单的 CLR 模块,则加载程序将抛出System.BadImageFormatException例外。最后,如果 CODEBASE 是使用除file:,调用者必须具有 WebPermission 访问权限,否则System.SecurityException抛出异常。此外,URL 上的程序集除了file:在加载之前首先下载到下载缓存。

清单 2.2 显示了一个简单的 C# 程序,它加载位于file://C:/usr/bin/xyzzy.dll然后创建名为的包含类型的实例AcmeCorp.LOB.Customer。在此示例中,调用者提供的只是程序集的物理位置。 当程序以这种方式使用程序集加载器时,CLR 会忽略程序集的四部分名称,包括其版本号。

示例 2. 2. 使用显式代码库加载程序集

using System;
using System.Reflection;
public class Utilities {
  public static Object LoadCustomerType() {
    Assembly a = Assembly.LoadFrom(
                    "file: //C:/usr/bin/xyzzy. dll") ;
    return a.CreateInstance("AcmeCorp.LOB.Customer") ;
  }
}

尽管按位置加载程序集有些有趣,但大多数程序集都是使用程序集解析器按名称加载的。程序集解析器使用由四部分组成的程序集名称来确定使用程序集加载器将哪个基础文件加载到内存中。如图所示图2.9 http://my.safaribooksonline.com/0-201-73411-7/ch02lev1sec5#X2ludGVybmFsX0ZsYXNoUmVhZGVyP3htbGlkPTAtMjAxLTczNDExLTcvMjM=,这个名称到位置解析过程考虑了多种因素,包括应用程序所在的目录、版本控制策略和其他配置细节(所有这些都将在本章后面讨论)。

程序集解析器通过以下方式向开发人员公开Load的方法System.Reflection.Assembly班级。如清单 2.3 所示,此方法接受一个由四部分组成的程序集名称(作为字符串或作为 AssemblyName 引用),表面上看起来与程序集加载器公开的 LoadFrom 方法类似。这种相似性只是表面的,因为 Load 方法首先使用程序集解析器,通过一系列相当复杂的操作来查找合适的文件。这些操作中的第一个是应用版本策略来准确确定应加载所需程序集的哪个版本。

例 2.3。使用程序集解析器加载程序集

using System;
using System.Reflection;
public class Utilities {
  public static Object LoadCustomerType() {
    Assembly a = Assembly.Load(
      "xyzzy, Version=1. 2. 3.4, " +
      "Culture=neutral, PublicKeyToken=9a33f27632997fcc") ;
    return a.CreateInstance("AcmeCorp.LOB.Customer") ;
  }
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

CLR 如何加载 DLL? 的相关文章

  • 检查数据库中是否存在记录

    我正在使用这些代码行来检查记录是否存在 SqlCommand check User Name new SqlCommand SELECT FROM Table WHERE user txtBox UserName Text conn int
  • 如何从对Web服务发出的请求中获取客户端IP地址

    我的 IIS 中托管有一个 Web 服务 当客户端直接使用我的服务时 我需要找出客户端 IP 地址 like http MyIpAddress MyApplication MyWebServiceClass asmx http MyIpAd
  • 如何将动态数据写入 MVC 3 Razor 中的页面布局?

    我有带有 Razor 引擎的 MVC 3 C 项目 将动态数据写入 Layout cshtml 的方法和最佳实践是什么 例如 也许我想在网站的右上角显示用户名 该名称来自会话 数据库或基于用户登录的任何内容 更新 我也在寻找将某些数据渲染到
  • 从 unsigned char* 到 char* 的转换无效

    这是一个代码 1 int main int argc char argv 2 3 signed char S psc 4 unsigned char U pusc 5 char C pc 6 7 C S 8 C U 9 10 pc psc
  • ptrace和waitpid有什么关系?

    我正在练习使用ptrace但我不太了解它和之间的关系waitpid 这是我的测试程序 int main int argc char argv pid t pid 22092 if ptrace PTRACE ATTACH pid NULL
  • Python 相当于 Bit Twiddling Hacks 中的 C 代码?

    我有一个位计数方法 我正在尝试尽可能快地实现 我想尝试下面的算法位摆弄黑客 http graphics stanford edu seander bithacks html CountBitsSetParallel 但我不知道 C 什么是
  • 为基于架构的 XML 文件创建 WPF 编辑器

    这是场景 我们的服务器产品之一使用大型 XML 配置文件 该文件的布局相当好 并且针对 XSD 文件进行了验证 现在是时候构建一个配置 GUI 来维护这个文件了 我想深入研究 WPF 来完成它 我可以为每个配置部分布置一个单独的表单 每次向
  • 如何进行Visual Studio格式字典初始化?

    所有 Visual Studio 也包括 2012 不格式化以下内容 messageProcessor new Dictionary
  • C++ 中可以使用匿名类作为返回类型吗?

    有没有办法在 C 中使用匿名类作为返回类型 我用谷歌搜索这可能有效 struct Test fun 但是这段代码无法编译 错误信息是 新类型不能在返回类型中定义 其实代码没有任何意义 我只是想弄清楚匿名类是否可以用作C 中的返回类型 这是我
  • 在 T4 代码生成中,如何从引用的程序集中获取类型?

    由于 T4 在项目上下文之外运行 因此我无权访问当前程序集或其他程序集 如何注册对引用程序集的访问 然后从中获取类型 我猜您想访问项目中建筑物的程序集 我在下面的示例代码中所做的是将一个名为 TestLib 的项目添加到我的解决方案中 我将
  • WPF ComboBox 中具有本地化名称的枚举

    我有一个列出枚举的组合框 enum StatusEnum Open 1 Closed 2 InProgress 3
  • 是否可以在对Where 的调用中调用命名方法?

    我试图从 RedGate 的这本免费电子书中了解 Linq 的一些性能影响ftp support red gate com ebooks under the hood of net memory management part1 pdf f
  • 多个包含带有变量定义的头文件

    我只是构建一个简单的 C 项目 代码如下所示 head h ifndef HEAD H define HEAD H int my var 100 endif src1 cpp include head h src2 cpp include
  • 我应该使用 Helgrind 还是 DRD 进行线程错误检测?

    好像Valgrind http valgrind org docs manual manual html有两个工具都可以进行线程错误检测 Helgrind http valgrind org docs manual hg manual ht
  • 使用 C# 的异步 WebRequest

    您好 我有一个函数 它将 url Get 参数传递到网络服务器上的 php 文件 并等待文件的响应 通常需要 10 20 秒 我想将其放入一个循环中 因为我必须一次将这些 Get 请求发送到大约 5 个不同的 php 文件 但是当我尝试将其
  • C# 中的类和模块有什么用

    有人可以解释一下类和模块之间的区别吗 你什么时候使用其中一种而不是另一种 我正在使用 C 更新 我的意思是相当于 VB 模块的 C 版本 这在很大程度上取决于您所指的 模块 Visual Basic 的模块 C 中没有真正等效的 VB Ne
  • 在 boost 元组、zip_iterator 等上使用 std::get 和 std::tie

    我有哪些使用选择std get lt gt and std tie lt gt 与增强结构一起 例子 我想使用基于范围的 for 循环在多个容器上进行迭代 我可以实施zip函数 它使用boost zip iterator include
  • 智能感知不显示评论

    如果我在 Visual Studio 2010 中输入类似的内容数据集1 我得到所有可用方法和属性的列表 智能感知 这很好用 但是 如果我在此列表中选择一个方法或属性 我不会得到 if 的描述 例如 如果我有类似的东西 public cla
  • 查找文本文件中每行的行大小

    如何计算每行中的字符或数字数量 是否有类似 EOF 的东西更像是行尾 您可以遍历行中的每个字符并不断增加计数器直到行尾 n 遇到 确保以文本模式打开文件 r 而不是二进制模式 rb 否则流不会自动将不同平台的行结束序列转换为 n 人物 这是
  • 使用 List.Contains 方法为 LINQ 构建表达式树

    Problem 我正在重构一些LINQ查询我们的 Web 应用程序中的多个报告 并且我尝试将一些重复的查询谓词移至它们自己的中IQueryable扩展方法 以便我们可以将它们重新用于这些报告以及将来的报告 正如您可能推断的那样 我已经重构了

随机推荐

  • 在托管代码中 P/Invoking SetWindowLong 和 CallWindowProc(紧凑框架)

    我正在尝试使用 SetWindowLong 覆盖 winmobile 任务栏的窗口过程 以便捕获和阻止按下的按钮 我创建了一个类 其中包含一种用于重写的方法和一种用于恢复窗口过程的方法 MessageReceived 方法是我用来替换任务栏
  • 从代码注释中引用 TFS 工作项

    在 Visual Studio 2012 中 我想要从代码注释到 TFS 工作项的可单击引用 有没有一种简单的方法可以做到这一点 这也可以通过函数体内的注释 不是函数的摘要 来实现吗 所以我想要这样的东西
  • 如何使用c#仅获取目录中的文件名?

    当我使用下面的代码行时 我得到一个包含各个文件的整个路径的字符串数组 private string pdfFiles Directory GetFiles C Documents pdf 我想知道是否有一种方法可以只检索字符串中的文件名而不
  • 使用 spring 的条件 bean

    我正在尝试写一个ValidatorFactory这将根据其类型为我提供一个验证器 public Validator getNewValidator ValidatorType type switch case a new Validator
  • 如何修复创建新页面时的此错误?

    我有一个 Xamarin Forms 项目 在这个项目中 我已经有一个空白页面 但我添加了一个新页面 此时错误开始显示 显示的错误是 Error XLS0414 The type ContentPage was not found Veri
  • jQuery:检查字符串中是否存在特殊字符

    我知道这个问题在 Stack 上被问得更频繁 但我似乎无法从已经发布的问题中得到直接的答案 我需要检查所有特殊字符 除了 是否都在字符串中 如果是 则向用户发出警报 到目前为止我所拥有的是这样的 if Search val indexOf
  • 我可以在 C# *using* 块中拥有不同类型的对象吗?

    using Font font3 new Font Arial 10 0f font4 new Font Arial 10 0f Use font3 and font4 我知道可以在一个对象内使用多个相同类型的对象using clause
  • PhoneGap Build 版本 2.7.0 忽略 Android 上 config.xml 中的全屏首选项

    我已遵循此页面上非常明确的说明 https build phonegap com docs config xml https build phonegap com docs config xml 我已在 config xml 文件中包含以下
  • 有人能够正确使用 libsensors 吗?

    长话短说 我正在尝试编写一个可以检查CPU温度的应用程序 使用 libsensors 3 手册页 我至少能够获得 libsensors version 号 截至目前 这是我的代码 include
  • 在 Slack 上发布带有附加文件的消息

    我正在用 C 编写一个简单的控制台应用程序来与 Slack com 进行通信 我通过他们的 WebApi 执行此操作 目前我知道如何发布消息 带有附件 彩色 链接 用户等 并将文件发送到服务器 如果您以正常方式发送文件 键入文本框左侧的 上
  • 目录中的文件按文件名升序排序

    我有一个目录中的文件列表 我想按文件名对其进行排序 这是主要代码 var localPath this Server MapPath Content Img type var directory new DirectoryInfo loca
  • Date.toString() 显示哪个时区?

    默认情况下 方法执行哪个时区java util Date toString http download oracle com javase 6 docs api java util Date html toString 28 29展示 自从
  • 从服务器下载图像以显示在 CollectionView 上

    我正在开发一个用户可以出售 购买的产品应用程序 该应用程序基于集合视图 集合视图具有集合单元格 其中显示产品图像缩略图 以下代码从服务器获取产品图像 并等待下载所有图像 然后将它们显示在单元格中 以下代码有效 但用户需要等待 10 20 秒
  • 在 Woocommerce 3 中以编程方式更新产品库存

    我非常需要帮助 我正在尝试以编程方式更新 woocommerce 产品库存数量 我们通过一些 JSON 向我们提供了供应商提要 我可以从提要中读取股票 并可以正确地从帖子元中提取数据 我正在使用最新版本的 WP 和 WOO PHP 是 7
  • Android:显示一个对话框以启用 wifi

    我想 如果 wifi 被禁用 向用户显示一个对话框 可以决定他是否要启用或禁用 wifi 好吧 我可以查看 wifi 是否已启用 但我如何显示该设置对话框 这是我正在使用的代码 if wifiMan isWifiEnabled false
  • 在 spring3 控制器上返回“ModelAndView”或“String”哪个更好

    ModelAndView的返回方式 RequestMapping value list method RequestMethod GET public ModelAndView list UserAuth UserAuth user Mod
  • 是否可以在 MVC3 (C#) 中为 `[Display(Name="Something")]` 数据注释使用变量

    不知道为什么 但 MVC3 中的数据注释坚持具有常量值 我只是无法理解错误消息和显示名称等内容 我喜欢这些注释 它们非常易于使用且功能强大 但是如果您需要支持多种语言怎么办 想象一下我有以下模型 public class Person pu
  • 如何根据SSIS中的用户变量值在数据流中使用if..else

    I have a fairly straightforward SSIS package with a number of Data Flow tasks each with data flows for multiple tables l
  • 如何查看导致 clr.dll 中崩溃转储的 C# 代码?

    我有一个 Windows 窗体应用程序 NET 4 它在我的开发计算机上运行良好 但在其他两台测试计算机上崩溃 我可以加载它在 VS2010 中创建的小型转储 选择 使用混合调试 会导致 Visual Studio 明显无休止地滥用 CPU
  • CLR 如何加载 DLL?

    我的假设始终是 CLR 在应用程序域启动时加载了它所需的所有 DLL 然而 我写了一个例子 让我对这个假设提出质疑 我启动我的应用程序并检查加载了多少模块 Process ObjModulesList ProcessModuleCollec