代码之家  ›  专栏  ›  技术社区  ›  Keith Bloom

ASP.NET:查找内存不足扩展的原因

  •  2
  • Keith Bloom  · 技术社区  · 15 年前

    我试图找出一个网站内存不足的原因。这个站点有大约12000.aspx页,上一次崩溃时,我用adplus捕获了一个内存转储。

    经过一些调查,我发现很多堆碎片,大约有100MB的空闲块无法分配。在更深的地方挖掘一个大的物体堆是碎片状的,其原因似乎是如上文所述的绳子缠绕在一起。

    这可能是由于网站中的页数引起的吗?当它们都被编译时,它们就在记忆中,通过查看垃圾堆,它们被囚禁并固定住,我认为这意味着它们会停留一段时间。

    我会发现这很奇怪,因为有许多站点有更多的页面,但是动态编译可以解释内存的增长。

    还有什么其他方法可以找到内存泄漏的原因?我尝试在挂起模式下使用ADPLUS捕获转储,但失败了,IIS工作进程将被回收。

    〔1〕 Large Object Heap Fragmentation

    2 回复  |  直到 15 年前
        1
  •  0
  •   JoeBilly    15 年前

    是的,碎片是其中一个原因,因为它将更难'找到'记忆。

    一些众所周知的线索:

    • 在32位操作系统上,即使您的系统拥有更多内存,您的工作进程在内存中也不能超过2GB。另一种选择是/3GB开关(boot.ini文件)。

    • 当__process \ virtual bytes_157;在虚拟地址空间限制(通常为2 GB)的600 MB内时,出现内存不足异常的可能性开始显著增加,其次,测试表明__process \ virtual bytes_157;通常比__process \ private bytes_128;157大不超过600 MB。

    • clr正在按块分配和处理内存(内存64 MB;)。这并不意味着它使用了所有的内存,它意味着一个块在使用一个字节之前不会被释放,这就是内存如何变得碎片化的原因。

    • 当clr不能分配内存(需要新的块),并且不能垃圾收集或分页某些内存时,outofmemoryException将在最佳情况下发生,或者在最坏的情况下服务器将过载。

    • 关于动态编译,这是事实,但最重要的是 <compilation debug="false" /> / <deployment retail=”true”/> 开关。它们打开批编译,这意味着一个目录的DLL(这是另一个点),而不是每个“页面”一个导致虚拟空间碎片的DLL。

    • 每个目录大约有一个DLL,即使是批量编译,您拥有的目录/子目录越多,您拥有的DLL越多,您拥有的虚拟地址空间就越分散。

    就个人而言,我使用Ants内存分析器来查找内存问题。

        2
  •  0
  •   Wallace Breza    15 年前

    有一个很好的博客 here 作者是Tess Ferrandez,他在开发ASP.NET应用程序时谈到内存问题和其他类型的调试问题。

    post 特别是引导您通过一个教程来查看是否有泄漏。它使用了讨厌的windbg,但是她解释了所有的命令,这样你就可以清楚地看到你用过的内存,它精确地显示了哪些对象正在填满所有的空间。

    我曾多次使用她的站点来诊断内存泄漏和其他与性能相关的问题。

    我也用过类似的工具 DebugDiag 帮助捕获与内存相关的问题,并使用其内置的诊断工具来帮助查找问题。