GC.AddMemoryPressure [英] GC.AddMemoryPressure

查看:380
本文介绍了GC.AddMemoryPressure的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在用C#写一个使用第三方COM DLL的应用程序,这个dll在非托管内存中创建了很多资源(比如位图,视频,数据结构)。在周围挖掘我遇到垃圾收集器的以下呼吁:

$ p $ GC $ AddMemoryPressure long long bytesAllocated

它在MSDN中记录在这里:

http://msdn.microsoft.com/zh-cn/library/system .gc.addmemorypressure.aspx



这听起来像是我应该调用的东西,因为这个外部DLL创建了很多CLR不知道的资源。 / p>

我想我有两个问题...


  1. 我怎么知道当dll是第三方时需要添加很多内存压力,而且我无法确切知道该dll分配多少内存。
  2. 在任何混合的本地/受管进程中,都有本地/受管内存使用情况的混合。如果两者之间没有GC控制的关系,那么就不需要这个API。例如,如果托管代码中存在某些确定性状态更改会导致本机内存分配和释放,那么GC可以做的任何事情都不会强制本机内存被释放。



    但是,经常有由具有终结器的托管对象持有的本机内存。因此,GC 可以减少本地堆的大小,只需触发一个集合并获取这些终结器即可运行。

    因此,如果您有很多情况下,可能需要调用这个API(就像文档说的那样)。



    至于你应该告诉它多少,那很可能不是你可以通过纯粹的分析找到答案,尤其是第三方库。您需要运行性能监视器,运行一个分配大量第三方对象的测试,并查看Native Bytes和CLR内存计数器,以了解它们之间的关系。



    在使用COM对象时,实际上可以通过使用 Marshal.ReleaseComObject 。注意你需要使用一个愚蠢的循环来让它摆脱这个对象:

    $ $ $ $ $ $ $ c $ while while(Marshal.ReleaseComObject(obj) != 0)
    {
    }


    I am writing an application in C# that makes use of a 3rd party COM DLL, this dll creates a lot of resources (like bitmaps, video, data structures) in unmanaged memory. While digging around I came across the following call for the Garbage Collector:

    GC.AddMemoryPressure(long long bytesAllocated)
    

    It is documented in MSDN here:

    http://msdn.microsoft.com/en-us/library/system.gc.addmemorypressure.aspx

    This sounds like something I should be calling since this external dll is createing a lot of resources the CLR is unaware of.

    I guess I have two questions...

    1. How do I know how much memory pressure to add when the dll is 3rd party and it's not possible for me to know exactly how much memory this dll is allocating.
    2. How important is it to do this?

    解决方案

    In any mixed native/managed process, there is a mixture of native/managed memory usage. If there is no GC-controlled relationship between the two, then there would be no need for this API. For example, if there are certain deterministic state changes in the managed code that cause native memory to be allocated and deallocated, then nothing the GC can do will ever force native memory to be released.

    However, very often there is native memory held by managed objects that have finalizers. So the GC can reduce the size of the native heap, simply by triggering a collection and getting those finalizers to run.

    Therefore if you have a lot of that going on, it could well be necessary to call this API (just like the documentation says).

    As for how much you should tell it, that's probably not something you can cook up an answer for by pure analysis, especially with a 3rd party library. You need to run Performance Monitor, run a test that allocates a lot of the 3rd party objects, and look at the Native Bytes and CLR memory counters to see how they relate.

    As you're using a COM object, you could in fact deterministically force instances to clean up when you know you no longer need them, by using Marshal.ReleaseComObject. Note that you need to use a goofy loop to make it get rid of the object:

    while (Marshal.ReleaseComObject(obj) != 0) 
    {
    }
    

    这篇关于GC.AddMemoryPressure的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆