在我们的一台生产服务器上,w3wp.exe 对于 ASP.NET Core 应用程序使用 >600 MB 的专用内存。
我使用
dotnet-gcdump
进行了托管内存转储,但其中一个显示托管对象的内存使用量约为 23 MB。我还进行了完整的内存转储,但没有看到我可以访问的任何内容的高内存使用率。
执行 gcdump 应该清理所有未使用的内存,对吧?那么有些东西仍在积极使用所有这些 MB?
这里可能发生了什么?
答案是服务器垃圾收集器。
这是 ASP.NET(Core)应用程序的默认模式。它很少运行 GC,并默认保留大量 RAM,以防负载突然增加。
使用工作站垃圾收集器可以显着降低内存占用量(与桌面应用程序一样),但代价是垃圾收集周期更频繁,因此这是 CPU 和内存之间的权衡。
由于我的应用程序没有进行足够的处理来证明这么多内存的合理性,因此我将它们切换到工作站垃圾收集器模式,从那以后就再也没有出现过问题。
您可以通过两种方式做到这一点:
<ServerGarbageCollection>false</ServerGarbageCollection>
或
*.runtimeconfig.json
,将"System.GC.Server": true
更改为"System.GC.Server": false
第二个选项将自动从第一个选项产生,但它对于已经部署的应用程序很有用,而无需重建它们。