c ++ dll中的内存泄漏[重复]

Posted

技术标签:

【中文标题】c ++ dll中的内存泄漏[重复]【英文标题】:Memory leaks in c++ dll [duplicate] 【发布时间】:2013-06-15 04:51:42 【问题描述】:

我有一个简单的 c++ dll,其中包含用于屏幕捕获的代码。

HBITMAP hCaptureBitmap;

extern "C" __declspec(dllexport)  HBITMAP  __stdcall CaptureScreenByGDI(bool allScreens)

    int nScreenWidth;
    int nScreenHeight;
    HDC hDesktopDC;

    if(allScreens)
    
        nScreenWidth = GetSystemMetrics(SM_CXVIRTUALSCREEN);
        nScreenHeight = GetSystemMetrics(SM_CYVIRTUALSCREEN);
    
    else
    
        nScreenWidth = GetSystemMetrics(SM_CXSCREEN);
        nScreenHeight = GetSystemMetrics(SM_CYSCREEN);
    

    HWND hDesktopWnd = GetDesktopWindow();

    if(allScreens)
    
        hDesktopDC = GetDC(NULL);
    
    else
    
        hDesktopDC = GetDC(hDesktopWnd);
    

    HDC hCaptureDC = CreateCompatibleDC(hDesktopDC);
    hCaptureBitmap =CreateCompatibleBitmap(hDesktopDC, 
        nScreenWidth, nScreenHeight);

    SelectObject(hCaptureDC,hCaptureBitmap); 

    BitBlt(hCaptureDC,0,0,nScreenWidth,nScreenHeight,
        hDesktopDC,0,0,SRCCOPY|CAPTUREBLT); 

    ReleaseDC(hDesktopWnd,hDesktopDC);
    DeleteDC(hCaptureDC);

    return hCaptureBitmap;


extern "C" __declspec(dllexport)  void __stdcall ClearAfterGDI()

    DeleteObject(hCaptureBitmap);

调用后

CaptureScreenByGDI(true);
ClearAfterGDI();

来自 c# 的仍然存在内存泄漏。为什么? 如果我从 CaptureScreenByGDI 函数调用 DeleteObject(hCaptureBitmap) 并返回 void 一切都可以。

如何解决?

【问题讨论】:

应用程序验证器在某些情况下可能会有所帮助。 【参考方案1】:

您需要将旧位图保存在您创建的 DC 中并在删除 DC 之前将其恢复:

HGDIOBJ hBmpOld = SelectObject(hCaptureDC,hCaptureBitmap); 
...
SelectObject(hCaptureDC, hBmpOld);
DeleteDC(hCaptureDC);

【讨论】:

我真的不知道究竟是什么解决了这个问题,但是在我添加了你的代码 + DeleteObject(hCaptureBitmap) 在重新创建位图之前 + 在 c# 中添加 bmp.Dispose() 之后一切都很好)

以上是关于c ++ dll中的内存泄漏[重复]的主要内容,如果未能解决你的问题,请参考以下文章

C ++中的内存泄漏示例(通过使用异常)[重复]

C ++调用COM DLL中的函数可能发生内存泄漏

带有 .NET 的 C++ dll:内存泄漏是确定的吗?

C++/C# 应用程序中的内存泄漏

堆中的 DLL 内存泄漏

对于 C/C++ 程序及其插件 DLL,最好的免费内存泄漏检测器是啥? [关闭]