返回信息流用c#4.0写了一个异步socket的server,运行时间久了,内存占用巨大。用dotNet Memory Profiler工具看了一下程序占用内存的状况,Private Heap中,只有小部分是data,也就是对象,绝大部分内存都被GC hole 占用着。查了一下GC hole是什么,看到一个帖子是这样说的:
The code snippet below is the simplest way to introduce a GC hole into the system.
//OBJECTREF is a typedef for Object*.
{
PointerTable *pTBL = o_pObjectClass->GetPointerTable();
OBJECTREF aObj = AllocateObjectMemory(pTBL);
OBJECTREF bObj = AllocateObjectMemory(pTBL);
//WRONG!!! “aObj” may point to garbage if the second
//“AllocateObjectMemory” triggered a GC.
DoSomething (aOb, bObj);
}
All it does is allocate two managed objects, and then does something with them both.
This code compiles fine, and if you run simple pre-checkin tests, it will probably “work.” But this code will crash eventually.
Why? If the second call to “AllocateObjectMemory” triggers a GC, that GC discards the object instance you just assigned to “aObj”. This code, like all C++ code inside the CLR, is compiled by a non-managed compiler and the GC cannot know that “aObj” holds a root reference to an object you want kept live.
原文:
http://kaushalp.blogspot.com/2007/04/what-is-gc-hole-and-how-to-create-gc.html
这是一条镜像帖。来源:北邮人论坛 / dot-net / #3917同步于 2012/10/15
该镜像源已超过 30 天没有更新,可能在源站已被删除。
dotNET机器人发帖
求助!
geniuszty
2012/10/15镜像同步5 回复
订阅后,新回复会通过你的通知中心匿名送达。
5 条回复
按照这样说如果,下面的代码也会出错?
{
char[] val = {'a','b','c'};
String s = new String(val);
GC.Collect();
Console.Writeln(s);
}
非托管的资源会被GC引用吗?memory profiler是这样显示的,GC Gen#2和Gen0里的holes巨大
Managed heaps - xxxxxxxxxxxxxKB
Normal heap - xxxxxxxxxxxKB
Generation #0 - xxxxxxxxxKB
Data - xxxxKB
"Holes" - xxxxxxxxxKB
Generation #1 - xxKB
Data - 0KB
"Holes" - xKB
Generation #2 - xxxxxxxxxxxxxKB
Data - xxxxKB
"Holes" - xxxxxxxxxxxxxKB
Large heap - 131072KB
Large heap - 83KB
Overhead/unused - 130989KB
Overhead - 0KB
【 在 ahomer 的大作中提到: 】
: 是不是把C# 当 C++来写了?
: 申请了很多非托管的资源,而没有人工释放
那个帖子的意思是aObj 变成了野指针吗?
【 在 ahomer 的大作中提到: 】
: 是不是把C# 当 C++来写了?
: 申请了很多非托管的资源,而没有人工释放