我正在用 C# 编写一个高容量 Web 服务,该服务在 Win 2k8(.NET 4.5)上的 64 位 IIS 中运行,它与 XML 有效负载一起使用,并对小型和大型对象(主要是大型对象)执行各种操作字符串,一些超过 85k(所以进入 LOH))。请求是无状态的,并且内存使用随着时间的推移保持稳定。每个请求正在分配和释放大量内存,似乎没有内存泄漏。
每秒最多运行 25 个事务,平均调用持续 5 秒,根据两个分析工具,它在 GC 中花费了 40-60% 的时间,perfmon 在 5 秒内显示稳定的 20 次 G0 和 G1 收集,以及 15 G2 收集超过 5 秒 - 这意味着我们希望保留在 G0 中的数据有很多(我们认为)提前进入 G2。我读到的一切都表明这是非常过分的。我们预计系统应该能够以高于 25 tps 的吞吐量执行,并假设 GC 活动阻止了这种情况。
处理请求的机器有很多内存 - 16GB - 负载下的应用程序在负载下一个小时最多消耗 1GB。我知道更大的堆不一定会使事情变得更好,但是有备用内存。
我很欣赏这对细节很清楚(如果时间允许,将尝试用一个简单的应用程序重新创建条件) - 但谁能解释为什么我们看到如此多的 G2 GC 活动?我应该专注于 LOH 吗?人们一直告诉我 CLR 的 GC“适应”您的负载,但在这种情况下它并没有改变它的行为,而且与其他运行时不同,我似乎几乎无法调整它(尝试过工作站 GC,但有几乎没有可观察到的差异)。