From fc4ebe159018feed1e772831833516c395521172 Mon Sep 17 00:00:00 2001 From: Jactry Zeng Date: Thu, 14 Mar 2019 11:03:07 +0300 Subject: [PATCH] mfplat: Initialize attribute array. Signed-off-by: Jactry Zeng Signed-off-by: Nikolay Sivov Signed-off-by: Alexandre Julliard --- dlls/mfplat/buffer.c | 9 +++- dlls/mfplat/main.c | 80 ++++++++++++++++++++++++++++-------- dlls/mfplat/mediatype.c | 30 ++++++++++---- dlls/mfplat/mfplat_private.h | 13 +++++- 4 files changed, 107 insertions(+), 25 deletions(-) diff --git a/dlls/mfplat/buffer.c b/dlls/mfplat/buffer.c index f6eecb68cb3..b07ec875f96 100644 --- a/dlls/mfplat/buffer.c +++ b/dlls/mfplat/buffer.c @@ -271,6 +271,7 @@ static ULONG WINAPI sample_Release(IMFSample *iface) { for (i = 0; i < sample->buffer_count; ++i) IMFMediaBuffer_Release(sample->buffers[i]); + clear_attributes_object(&sample->attributes); DeleteCriticalSection(&sample->cs); heap_free(sample->buffers); heap_free(sample); @@ -704,6 +705,7 @@ static const IMFSampleVtbl samplevtbl = HRESULT WINAPI MFCreateSample(IMFSample **sample) { struct sample *object; + HRESULT hr; TRACE("%p.\n", sample); @@ -711,7 +713,12 @@ HRESULT WINAPI MFCreateSample(IMFSample **sample) if (!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } + object->IMFSample_iface.lpVtbl = &samplevtbl; InitializeCriticalSection(&object->cs); diff --git a/dlls/mfplat/main.c b/dlls/mfplat/main.c index c8c19aa404f..9d8a3ae2fe5 100644 --- a/dlls/mfplat/main.c +++ b/dlls/mfplat/main.c @@ -628,17 +628,18 @@ static ULONG WINAPI mfattributes_AddRef(IMFAttributes *iface) static ULONG WINAPI mfattributes_Release(IMFAttributes *iface) { - mfattributes *This = impl_from_IMFAttributes(iface); - ULONG ref = InterlockedDecrement(&This->ref); + struct attributes *attributes = impl_from_IMFAttributes(iface); + ULONG refcount = InterlockedDecrement(&attributes->ref); - TRACE("(%p) ref=%u\n", This, ref); + TRACE("%p, refcount %d.\n", iface, refcount); - if (!ref) + if (!refcount) { - HeapFree(GetProcessHeap(), 0, This); + clear_attributes_object(attributes); + heap_free(attributes); } - return ref; + return refcount; } static HRESULT WINAPI mfattributes_GetItem(IMFAttributes *iface, REFGUID key, PROPVARIANT *value) @@ -909,10 +910,34 @@ static const IMFAttributesVtbl mfattributes_vtbl = mfattributes_CopyAllItems }; -void init_attribute_object(mfattributes *object, UINT32 size) +HRESULT init_attributes_object(struct attributes *object, UINT32 size) { - object->ref = 1; object->IMFAttributes_iface.lpVtbl = &mfattributes_vtbl; + object->ref = 1; + InitializeCriticalSection(&object->cs); + + object->attributes = NULL; + object->count = 0; + object->capacity = 0; + if (!mf_array_reserve((void **)&object->attributes, &object->capacity, size, + sizeof(*object->attributes))) + { + DeleteCriticalSection(&object->cs); + return E_OUTOFMEMORY; + } + + return S_OK; +} + +void clear_attributes_object(struct attributes *object) +{ + size_t i; + + for (i = 0; i < object->count; i++) + PropVariantClear(&object->attributes[i].value); + heap_free(object->attributes); + + DeleteCriticalSection(&object->cs); } /*********************************************************************** @@ -920,15 +945,20 @@ void init_attribute_object(mfattributes *object, UINT32 size) */ HRESULT WINAPI MFCreateAttributes(IMFAttributes **attributes, UINT32 size) { - mfattributes *object; + struct attributes *object; + HRESULT hr; TRACE("%p, %d\n", attributes, size); - object = HeapAlloc( GetProcessHeap(), 0, sizeof(*object) ); - if(!object) + object = heap_alloc_zero(sizeof(*object)); + if (!object) return E_OUTOFMEMORY; - init_attribute_object(object, size); + if (FAILED(hr = init_attributes_object(object, size))) + { + heap_free(object); + return hr; + } *attributes = &object->IMFAttributes_iface; return S_OK; @@ -990,6 +1020,7 @@ static ULONG WINAPI mfbytestream_Release(IMFByteStream *iface) if (!ref) { + clear_attributes_object(&This->attributes); HeapFree(GetProcessHeap(), 0, This); } @@ -1223,6 +1254,7 @@ static const IMFAttributesVtbl mfbytestream_attributes_vtbl = HRESULT WINAPI MFCreateMFByteStreamOnStream(IStream *stream, IMFByteStream **bytestream) { mfbytestream *object; + HRESULT hr; TRACE("(%p, %p): stub\n", stream, bytestream); @@ -1230,7 +1262,11 @@ HRESULT WINAPI MFCreateMFByteStreamOnStream(IStream *stream, IMFByteStream **byt if(!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } object->IMFByteStream_iface.lpVtbl = &mfbytestream_vtbl; object->attributes.IMFAttributes_iface.lpVtbl = &mfbytestream_attributes_vtbl; @@ -1248,6 +1284,7 @@ HRESULT WINAPI MFCreateFile(MF_FILE_ACCESSMODE accessmode, MF_FILE_OPENMODE open DWORD filecreation_disposition = 0; DWORD fileattributes = 0; HANDLE file; + HRESULT hr; FIXME("(%d, %d, %d, %s, %p): stub\n", accessmode, openmode, flags, debugstr_w(url), bytestream); @@ -1301,7 +1338,11 @@ HRESULT WINAPI MFCreateFile(MF_FILE_ACCESSMODE accessmode, MF_FILE_OPENMODE open if(!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } object->IMFByteStream_iface.lpVtbl = &mfbytestream_vtbl; object->attributes.IMFAttributes_iface.lpVtbl = &mfbytestream_attributes_vtbl; @@ -1457,6 +1498,7 @@ static ULONG WINAPI mfpresentationdescriptor_Release(IMFPresentationDescriptor * if (!ref) { + clear_attributes_object(&This->attributes); HeapFree(GetProcessHeap(), 0, This); } @@ -1855,7 +1897,7 @@ static HRESULT WINAPI mfsource_CreatePresentationDescriptor(IMFMediaSource *ifac if (!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + init_attributes_object(&object->attributes, 0); object->IMFPresentationDescriptor_iface.lpVtbl = &mfpresentationdescriptor_vtbl; *descriptor = &object->IMFPresentationDescriptor_iface; @@ -2754,6 +2796,7 @@ static ULONG WINAPI mfmediaevent_Release(IMFMediaEvent *iface) if (!ref) { + clear_attributes_object(&event->attributes); PropVariantClear(&event->value); heap_free(event); } @@ -3035,6 +3078,7 @@ HRESULT WINAPI MFCreateMediaEvent(MediaEventType type, REFGUID extended_type, HR const PROPVARIANT *value, IMFMediaEvent **event) { mfmediaevent *object; + HRESULT hr; TRACE("%#x, %s, %08x, %p, %p\n", type, debugstr_guid(extended_type), status, value, event); @@ -3042,7 +3086,11 @@ HRESULT WINAPI MFCreateMediaEvent(MediaEventType type, REFGUID extended_type, HR if(!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } object->IMFMediaEvent_iface.lpVtbl = &mfmediaevent_vtbl; object->type = type; diff --git a/dlls/mfplat/mediatype.c b/dlls/mfplat/mediatype.c index d27d5ef12b7..b526509ab31 100644 --- a/dlls/mfplat/mediatype.c +++ b/dlls/mfplat/mediatype.c @@ -116,6 +116,7 @@ static ULONG WINAPI mediatype_Release(IMFMediaType *iface) if (!refcount) { + clear_attributes_object(&media_type->attributes); heap_free(media_type); } @@ -496,6 +497,7 @@ static const IMFMediaTypeVtbl mediatypevtbl = HRESULT WINAPI MFCreateMediaType(IMFMediaType **media_type) { struct media_type *object; + HRESULT hr; TRACE("%p.\n", media_type); @@ -506,7 +508,11 @@ HRESULT WINAPI MFCreateMediaType(IMFMediaType **media_type) if (!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } object->IMFMediaType_iface.lpVtbl = &mediatypevtbl; *media_type = &object->IMFMediaType_iface; @@ -561,6 +567,7 @@ static ULONG WINAPI stream_descriptor_Release(IMFStreamDescriptor *iface) heap_free(stream_desc->media_types); if (stream_desc->current_type) IMFMediaType_Release(stream_desc->current_type); + clear_attributes_object(&stream_desc->attributes); DeleteCriticalSection(&stream_desc->cs); heap_free(stream_desc); } @@ -950,6 +957,7 @@ HRESULT WINAPI MFCreateStreamDescriptor(DWORD identifier, DWORD count, { struct stream_desc *object; unsigned int i; + HRESULT hr; TRACE("%d, %d, %p, %p.\n", identifier, count, types, descriptor); @@ -960,14 +968,19 @@ HRESULT WINAPI MFCreateStreamDescriptor(DWORD identifier, DWORD count, if (!object) return E_OUTOFMEMORY; - init_attribute_object(&object->attributes, 0); + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + { + heap_free(object); + return hr; + } object->IMFStreamDescriptor_iface.lpVtbl = &streamdescriptorvtbl; object->IMFMediaTypeHandler_iface.lpVtbl = &mediatypehandlervtbl; object->identifier = identifier; object->media_types = heap_alloc(count * sizeof(*object->media_types)); + InitializeCriticalSection(&object->cs); if (!object->media_types) { - heap_free(object); + IMFStreamDescriptor_Release(&object->IMFStreamDescriptor_iface); return E_OUTOFMEMORY; } for (i = 0; i < count; ++i) @@ -977,7 +990,6 @@ HRESULT WINAPI MFCreateStreamDescriptor(DWORD identifier, DWORD count, IMFMediaType_AddRef(object->media_types[i]); } object->media_types_count = count; - InitializeCriticalSection(&object->cs); *descriptor = &object->IMFStreamDescriptor_iface; @@ -1027,6 +1039,7 @@ static ULONG WINAPI presentation_descriptor_Release(IMFPresentationDescriptor *i if (presentation_desc->descriptors[i].descriptor) IMFStreamDescriptor_Release(presentation_desc->descriptors[i].descriptor); } + clear_attributes_object(&presentation_desc->attributes); DeleteCriticalSection(&presentation_desc->cs); heap_free(presentation_desc->descriptors); heap_free(presentation_desc); @@ -1369,16 +1382,19 @@ static const IMFPresentationDescriptorVtbl presentationdescriptorvtbl = static HRESULT presentation_descriptor_init(struct presentation_desc *object, DWORD count) { - init_attribute_object(&object->attributes, 0); + HRESULT hr; + + if (FAILED(hr = init_attributes_object(&object->attributes, 0))) + return hr; object->IMFPresentationDescriptor_iface.lpVtbl = &presentationdescriptorvtbl; object->descriptors = heap_alloc_zero(count * sizeof(*object->descriptors)); + InitializeCriticalSection(&object->cs); if (!object->descriptors) { - heap_free(object); + IMFPresentationDescriptor_Release(&object->IMFPresentationDescriptor_iface); return E_OUTOFMEMORY; } object->count = count; - InitializeCriticalSection(&object->cs); return S_OK; } diff --git a/dlls/mfplat/mfplat_private.h b/dlls/mfplat/mfplat_private.h index c42570c8a9b..7d2e25f4356 100644 --- a/dlls/mfplat/mfplat_private.h +++ b/dlls/mfplat/mfplat_private.h @@ -24,13 +24,24 @@ #include "wine/heap.h" +struct attribute +{ + GUID key; + PROPVARIANT value; +}; + typedef struct attributes { IMFAttributes IMFAttributes_iface; LONG ref; + CRITICAL_SECTION cs; + struct attribute *attributes; + size_t capacity; + size_t count; } mfattributes; -extern void init_attribute_object(mfattributes *object, UINT32 size) DECLSPEC_HIDDEN; +extern HRESULT init_attributes_object(struct attributes *object, UINT32 size) DECLSPEC_HIDDEN; +extern void clear_attributes_object(struct attributes *object) DECLSPEC_HIDDEN; extern void init_system_queues(void) DECLSPEC_HIDDEN; extern void shutdown_system_queues(void) DECLSPEC_HIDDEN;