【问题标题】:Memory leaks in c++ dll [duplicate]c ++ dll中的内存泄漏[重复]
【发布时间】: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 一切都可以。

如何解决?

【问题讨论】:

  • 应用程序验证器在某些情况下可能会有所帮助。

标签: c++ winapi memory-leaks gdi


【解决方案1】:

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

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

【讨论】:

  • 我真的不知道究竟是什么解决了这个问题,但是在我添加了你的代码 + DeleteObject(hCaptureBitmap) 在重新创建位图之前 + 在 c# 中添加 bmp.Dispose() 之后一切都很好)
猜你喜欢
  • 2012-09-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-12-25
  • 2013-07-01
  • 2017-10-01
  • 1970-01-01
相关资源
最近更新 更多