mirror of
https://github.com/gnif/LookingGlass.git
synced 2024-11-25 23:07:18 +00:00
[host] dxgi: fixed MFT memory leak and re-init failure
This commit is contained in:
parent
076a45acc5
commit
9ef9f60505
@ -249,8 +249,10 @@ bool DXGI::InitH264Capture()
|
|||||||
|
|
||||||
ID3D10MultithreadPtr mt(m_device);
|
ID3D10MultithreadPtr mt(m_device);
|
||||||
mt->SetMultithreadProtected(TRUE);
|
mt->SetMultithreadProtected(TRUE);
|
||||||
|
SafeRelease(&mt);
|
||||||
|
|
||||||
m_encodeEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
|
m_encodeEvent = CreateEvent(NULL, TRUE , FALSE, NULL);
|
||||||
|
m_shutdownEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
|
||||||
InitializeCriticalSection(&m_encodeCS);
|
InitializeCriticalSection(&m_encodeCS);
|
||||||
|
|
||||||
typeInfo.guidMajorType = MFMediaType_Video;
|
typeInfo.guidMajorType = MFMediaType_Video;
|
||||||
@ -285,14 +287,15 @@ bool DXGI::InitH264Capture()
|
|||||||
delete[] name;
|
delete[] name;
|
||||||
}
|
}
|
||||||
|
|
||||||
status = activationPointers[0]->ActivateObject(IID_PPV_ARGS(&m_mfTransform));
|
m_mfActivation = activationPointers[0];
|
||||||
|
CoTaskMemFree(activationPointers);
|
||||||
|
|
||||||
|
status = m_mfActivation->ActivateObject(IID_PPV_ARGS(&m_mfTransform));
|
||||||
if (FAILED(status))
|
if (FAILED(status))
|
||||||
{
|
{
|
||||||
CoTaskMemFree(activationPointers);
|
|
||||||
DEBUG_WINERROR("Failed to create H264 encoder MFT", status);
|
DEBUG_WINERROR("Failed to create H264 encoder MFT", status);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
CoTaskMemFree(activationPointers);
|
|
||||||
|
|
||||||
IMFAttributesPtr attribs;
|
IMFAttributesPtr attribs;
|
||||||
m_mfTransform->GetAttributes(&attribs);
|
m_mfTransform->GetAttributes(&attribs);
|
||||||
@ -348,7 +351,7 @@ bool DXGI::InitH264Capture()
|
|||||||
outType->SetGUID (MF_MT_SUBTYPE , MFVideoFormat_H264);
|
outType->SetGUID (MF_MT_SUBTYPE , MFVideoFormat_H264);
|
||||||
outType->SetUINT32(MF_MT_AVG_BITRATE , 240000);
|
outType->SetUINT32(MF_MT_AVG_BITRATE , 240000);
|
||||||
outType->SetUINT32(MF_MT_INTERLACE_MODE , MFVideoInterlace_Progressive);
|
outType->SetUINT32(MF_MT_INTERLACE_MODE , MFVideoInterlace_Progressive);
|
||||||
outType->SetUINT32(MF_MT_MPEG2_PROFILE , eAVEncH264VProfile_444);
|
outType->SetUINT32(MF_MT_MPEG2_PROFILE , eAVEncH264VProfile_422);
|
||||||
outType->SetUINT32(MF_MT_ALL_SAMPLES_INDEPENDENT, TRUE);
|
outType->SetUINT32(MF_MT_ALL_SAMPLES_INDEPENDENT, TRUE);
|
||||||
|
|
||||||
MFSetAttributeSize (outType, MF_MT_FRAME_SIZE , m_width, m_height);
|
MFSetAttributeSize (outType, MF_MT_FRAME_SIZE , m_width, m_height);
|
||||||
@ -356,6 +359,7 @@ bool DXGI::InitH264Capture()
|
|||||||
MFSetAttributeRatio(outType, MF_MT_PIXEL_ASPECT_RATIO, 1, 1);
|
MFSetAttributeRatio(outType, MF_MT_PIXEL_ASPECT_RATIO, 1, 1);
|
||||||
|
|
||||||
status = m_mfTransform->SetOutputType(0, outType, 0);
|
status = m_mfTransform->SetOutputType(0, outType, 0);
|
||||||
|
SafeRelease(&outType);
|
||||||
if (FAILED(status))
|
if (FAILED(status))
|
||||||
{
|
{
|
||||||
DEBUG_WINERROR("Failed to set the output media type on the H264 encoder MFT", status);
|
DEBUG_WINERROR("Failed to set the output media type on the H264 encoder MFT", status);
|
||||||
@ -375,6 +379,7 @@ bool DXGI::InitH264Capture()
|
|||||||
MFSetAttributeRatio(inType, MF_MT_PIXEL_ASPECT_RATIO, 1 , 1);
|
MFSetAttributeRatio(inType, MF_MT_PIXEL_ASPECT_RATIO, 1 , 1);
|
||||||
|
|
||||||
status = m_mfTransform->SetInputType(0, inType, 0);
|
status = m_mfTransform->SetInputType(0, inType, 0);
|
||||||
|
SafeRelease(&inType);
|
||||||
if (FAILED(status))
|
if (FAILED(status))
|
||||||
{
|
{
|
||||||
DEBUG_WINERROR("Failed to set the input media type on the H264 encoder MFT", status);
|
DEBUG_WINERROR("Failed to set the input media type on the H264 encoder MFT", status);
|
||||||
@ -408,6 +413,14 @@ bool DXGI::InitH264Capture()
|
|||||||
|
|
||||||
void DXGI::DeInitialize()
|
void DXGI::DeInitialize()
|
||||||
{
|
{
|
||||||
|
if (m_mediaEventGen)
|
||||||
|
{
|
||||||
|
m_mfTransform->ProcessMessage(MFT_MESSAGE_NOTIFY_END_OF_STREAM, NULL);
|
||||||
|
m_mfTransform->ProcessMessage(MFT_MESSAGE_COMMAND_DRAIN, NULL);
|
||||||
|
while (WaitForSingleObject(m_shutdownEvent, INFINITE) != WAIT_OBJECT_0) {}
|
||||||
|
m_mfTransform->DeleteInputStream(0);
|
||||||
|
}
|
||||||
|
|
||||||
if (m_releaseFrame)
|
if (m_releaseFrame)
|
||||||
{
|
{
|
||||||
m_releaseFrame = false;
|
m_releaseFrame = false;
|
||||||
@ -427,23 +440,32 @@ void DXGI::DeInitialize()
|
|||||||
m_surfaceMapped = false;
|
m_surfaceMapped = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SafeRelease(&m_mediaEventGen);
|
||||||
|
SafeRelease(&m_mfTransform);
|
||||||
|
SafeRelease(&m_mfDeviceManager);
|
||||||
|
|
||||||
SafeRelease(&m_texture);
|
SafeRelease(&m_texture);
|
||||||
SafeRelease(&m_dup);
|
SafeRelease(&m_dup);
|
||||||
SafeRelease(&m_output);
|
SafeRelease(&m_output);
|
||||||
SafeRelease(&m_deviceContext);
|
SafeRelease(&m_deviceContext);
|
||||||
SafeRelease(&m_device);
|
SafeRelease(&m_device);
|
||||||
SafeRelease(&m_dxgiFactory);
|
SafeRelease(&m_dxgiFactory);
|
||||||
SafeRelease(&m_mfTransform);
|
|
||||||
SafeRelease(&m_mfDeviceManager);
|
|
||||||
SafeRelease(&m_mediaEventGen);
|
|
||||||
|
|
||||||
if (m_encodeEvent)
|
if (m_encodeEvent)
|
||||||
{
|
{
|
||||||
CloseHandle(m_encodeEvent);
|
CloseHandle(m_encodeEvent );
|
||||||
m_encodeEvent = NULL;
|
CloseHandle(m_shutdownEvent);
|
||||||
|
m_encodeEvent = NULL;
|
||||||
|
m_shutdownEvent = NULL;
|
||||||
DeleteCriticalSection(&m_encodeCS);
|
DeleteCriticalSection(&m_encodeCS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (m_mfActivation)
|
||||||
|
{
|
||||||
|
m_mfActivation->ShutdownObject();
|
||||||
|
SafeRelease(&m_mfActivation);
|
||||||
|
}
|
||||||
|
|
||||||
m_initialized = false;
|
m_initialized = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -523,7 +545,9 @@ STDMETHODIMP Capture::DXGI::Invoke(IMFAsyncResult * pAsyncResult)
|
|||||||
DEBUG_WINERROR("MFT_MESSAGE_COMMAND_FLUSH", status);
|
DEBUG_WINERROR("MFT_MESSAGE_COMMAND_FLUSH", status);
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
SetEvent(m_shutdownEvent);
|
||||||
|
return S_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
case MEError:
|
case MEError:
|
||||||
@ -662,19 +686,19 @@ GrabStatus Capture::DXGI::GrabFrameTexture(FrameInfo & frame, ID3D11Texture2DPtr
|
|||||||
|
|
||||||
switch (shapeInfo.Type)
|
switch (shapeInfo.Type)
|
||||||
{
|
{
|
||||||
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR: frame.cursor.type = CURSOR_TYPE_COLOR; break;
|
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR : frame.cursor.type = CURSOR_TYPE_COLOR; break;
|
||||||
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR: frame.cursor.type = CURSOR_TYPE_MASKED_COLOR; break;
|
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR: frame.cursor.type = CURSOR_TYPE_MASKED_COLOR; break;
|
||||||
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME: frame.cursor.type = CURSOR_TYPE_MONOCHROME; break;
|
case DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME : frame.cursor.type = CURSOR_TYPE_MONOCHROME; break;
|
||||||
default:
|
default:
|
||||||
DEBUG_ERROR("Invalid cursor type");
|
DEBUG_ERROR("Invalid cursor type");
|
||||||
return GRAB_STATUS_ERROR;
|
return GRAB_STATUS_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
frame.cursor.hasShape = true;
|
frame.cursor.hasShape = true;
|
||||||
frame.cursor.shape = m_pointer;
|
frame.cursor.shape = m_pointer;
|
||||||
frame.cursor.w = shapeInfo.Width;
|
frame.cursor.w = shapeInfo.Width;
|
||||||
frame.cursor.h = shapeInfo.Height;
|
frame.cursor.h = shapeInfo.Height;
|
||||||
frame.cursor.pitch = shapeInfo.Pitch;
|
frame.cursor.pitch = shapeInfo.Pitch;
|
||||||
frame.cursor.dataSize = m_pointerSize;
|
frame.cursor.dataSize = m_pointerSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -815,6 +839,7 @@ GrabStatus Capture::DXGI::GrabFrameH264(FrameInfo & frame)
|
|||||||
status = MFCreateDXGISurfaceBuffer(__uuidof(ID3D11Texture2D), src, 0, FALSE, &buffer);
|
status = MFCreateDXGISurfaceBuffer(__uuidof(ID3D11Texture2D), src, 0, FALSE, &buffer);
|
||||||
if (FAILED(status))
|
if (FAILED(status))
|
||||||
{
|
{
|
||||||
|
SafeRelease(&src);
|
||||||
DEBUG_WINERROR("Failed to create DXGI surface buffer from texture", status);
|
DEBUG_WINERROR("Failed to create DXGI surface buffer from texture", status);
|
||||||
return GRAB_STATUS_ERROR;
|
return GRAB_STATUS_ERROR;
|
||||||
}
|
}
|
||||||
|
@ -143,11 +143,14 @@ namespace Capture
|
|||||||
bool m_surfaceMapped;
|
bool m_surfaceMapped;
|
||||||
|
|
||||||
HANDLE m_encodeEvent;
|
HANDLE m_encodeEvent;
|
||||||
bool m_encodeNeedsData, m_encodeHasData;
|
HANDLE m_shutdownEvent;
|
||||||
|
bool m_encodeNeedsData;
|
||||||
|
bool m_encodeHasData;
|
||||||
CRITICAL_SECTION m_encodeCS;
|
CRITICAL_SECTION m_encodeCS;
|
||||||
|
|
||||||
UINT m_resetToken;
|
UINT m_resetToken;
|
||||||
IMFDXGIDeviceManagerPtr m_mfDeviceManager;
|
IMFDXGIDeviceManagerPtr m_mfDeviceManager;
|
||||||
|
IMFActivatePtr m_mfActivation;
|
||||||
IMFTransformPtr m_mfTransform;
|
IMFTransformPtr m_mfTransform;
|
||||||
IMFMediaEventGeneratorPtr m_mediaEventGen;
|
IMFMediaEventGeneratorPtr m_mediaEventGen;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user