我的问题基本上与DLL和.NET有关。我们有一个应用程序正在使用相当多的内存,我们正在尝试弄清楚如何正确地测量它,特别是当问题主要出现在客户机上时。
有一件事情使我想到,那就是我们有一些相当大的带有生成的ORM代码的.NET程序集。
如果我使用一个具有唯一基地址的未托管(Win32)DLL,则同一台机器上的多个并行进程将把DLL加载到物理内存中一次,并将其映射到虚拟内存中供所有应用程序使用。因此,物理内存只会用于此DLL一次。
问题是.NET程序集会发生什么情况。这个DLL包含IL,虽然其中的部分可能在应用程序之间共享,但是由此产生的JITted代码怎么样?它是共享的吗?如果没有,我该如何衡量以确定它是否真正导致问题或不是? (是的,我知道,它会起作用,但在它成为最大的问题之前,我不会花太多时间在这上面)。
此外,我知道我们还没有查看解决方案中所有.NET程序集的基地址,对于.NET程序集来说,这是必要的吗?如果是这样,是否有一些指导方针可用于确定这些地址?
任何关于此领域的见解都将非常受欢迎,即使最终证明这不是一个大问题,甚至根本不是问题。
编辑:刚刚发现这个问题:.NET程序集和DLL调整基址部分回答了我的问题,但我仍然想知道JITted代码如何影响所有这些。
从那个问题及其被接受的答案中可以看出,JITted代码放置在堆上,这意味着每个进程将加载共享二进制程序集图像,并在其自己的内存空间中生成私有的JITted代码副本。
有没有办法可以测量这个呢?如果生成的代码很多,我们就需要更仔细地查看生成的代码,以确定是否需要调整它。
编辑:在此添加一些较短的问题:
- 确保.NET程序集的基地址唯一且不重叠,以避免将大部分用于获取JIT编译的IL代码的dll重新定位,是否有意义?
- 如何测量用于JIT编译的代码使用了多少内存,以确定这是否真的是一个问题?
@Brian Rasmussen在这里回答说,像我预期的那样,JIT会产生每个进程副本的JIT编译的代码。但重新定位程序集实际上会对减少内存使用有影响。我将不得不深入WinDbg+SoS工具中,这是我已经列在清单上一段时间的事情,但现在我怀疑我再也不能拖延了 :)
编辑:我在这方面找到了一些链接: