From: Derek Lesho dlesho@codeweavers.com
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com ---
v2: still keep a reference to the original type.
dlls/mf/samplegrabber.c | 17 ++++--- dlls/mf/tests/mf.c | 104 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 115 insertions(+), 6 deletions(-)
diff --git a/dlls/mf/samplegrabber.c b/dlls/mf/samplegrabber.c index 54e28b466c5..f60ce2a8433 100644 --- a/dlls/mf/samplegrabber.c +++ b/dlls/mf/samplegrabber.c @@ -72,6 +72,7 @@ struct sample_grabber IMFSampleGrabberSinkCallback *callback; IMFSampleGrabberSinkCallback2 *callback2; IMFMediaType *media_type; + IMFMediaType *current_media_type; BOOL is_shut_down; IMFMediaEventQueue *event_queue; IMFMediaEventQueue *stream_event_queue; @@ -572,7 +573,8 @@ static ULONG WINAPI sample_grabber_stream_type_handler_Release(IMFMediaTypeHandl
static HRESULT sample_grabber_stream_is_media_type_supported(struct sample_grabber *grabber, IMFMediaType *in_type) { - const DWORD supported_flags = MF_MEDIATYPE_EQUAL_MAJOR_TYPES | MF_MEDIATYPE_EQUAL_FORMAT_TYPES; + const DWORD supported_flags = MF_MEDIATYPE_EQUAL_MAJOR_TYPES | MF_MEDIATYPE_EQUAL_FORMAT_TYPES | + MF_MEDIATYPE_EQUAL_FORMAT_DATA; DWORD flags;
if (grabber->is_shut_down) @@ -631,9 +633,9 @@ static HRESULT WINAPI sample_grabber_stream_type_handler_SetCurrentMediaType(IMF if (FAILED(hr = sample_grabber_stream_is_media_type_supported(grabber, media_type))) return hr;
- IMFMediaType_Release(grabber->media_type); - grabber->media_type = media_type; - IMFMediaType_AddRef(grabber->media_type); + IMFMediaType_Release(grabber->current_media_type); + grabber->current_media_type = media_type; + IMFMediaType_AddRef(grabber->current_media_type);
return S_OK; } @@ -651,7 +653,7 @@ static HRESULT WINAPI sample_grabber_stream_type_handler_GetCurrentMediaType(IMF if (grabber->is_shut_down) return MF_E_STREAMSINK_REMOVED;
- *media_type = grabber->media_type; + *media_type = grabber->current_media_type; IMFMediaType_AddRef(*media_type);
return S_OK; @@ -669,7 +671,7 @@ static HRESULT WINAPI sample_grabber_stream_type_handler_GetMajorType(IMFMediaTy if (grabber->is_shut_down) return MF_E_STREAMSINK_REMOVED;
- return IMFMediaType_GetMajorType(grabber->media_type, type); + return IMFMediaType_GetMajorType(grabber->current_media_type, type); }
static const IMFMediaTypeHandlerVtbl sample_grabber_stream_type_handler_vtbl = @@ -840,6 +842,7 @@ static ULONG WINAPI sample_grabber_sink_Release(IMFMediaSink *iface) IMFSampleGrabberSinkCallback_Release(grabber->callback); if (grabber->callback2) IMFSampleGrabberSinkCallback2_Release(grabber->callback2); + IMFMediaType_Release(grabber->current_media_type); IMFMediaType_Release(grabber->media_type); if (grabber->event_queue) IMFMediaEventQueue_Release(grabber->event_queue); @@ -1411,6 +1414,8 @@ static HRESULT sample_grabber_create_object(IMFAttributes *attributes, void *use } object->media_type = context->media_type; IMFMediaType_AddRef(object->media_type); + object->current_media_type = context->media_type; + IMFMediaType_AddRef(object->current_media_type); IMFAttributes_GetUINT32(attributes, &MF_SAMPLEGRABBERSINK_IGNORE_CLOCK, &object->ignore_clock); IMFAttributes_GetUINT64(attributes, &MF_SAMPLEGRABBERSINK_SAMPLE_TIME_OFFSET, &object->sample_time_offset); list_init(&object->items); diff --git a/dlls/mf/tests/mf.c b/dlls/mf/tests/mf.c index 41ca385cc2b..fda80974724 100644 --- a/dlls/mf/tests/mf.c +++ b/dlls/mf/tests/mf.c @@ -2562,6 +2562,109 @@ static void test_sample_grabber(void) ok(hr == S_OK, "Failed to shut down, hr %#x.\n", hr); }
+static void test_sample_grabber_is_mediatype_supported(void) +{ + IMFMediaType *media_type, *media_type2, *media_type3; + IMFMediaTypeHandler *handler; + IMFActivate *activate; + IMFStreamSink *stream; + IMFMediaSink *sink; + ULONG refcount; + HRESULT hr; + GUID guid; + + /* IsMediaTypeSupported checks are done against the creation type, and check format data */ + hr = MFCreateMediaType(&media_type); + ok(hr == S_OK, "Failed to create media type, hr %#x.\n", hr); + + hr = IMFMediaType_SetGUID(media_type, &MF_MT_MAJOR_TYPE, &MFMediaType_Audio); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + hr = IMFMediaType_SetGUID(media_type, &MF_MT_SUBTYPE, &MFAudioFormat_PCM); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + hr = IMFMediaType_SetUINT32(media_type, &MF_MT_AUDIO_SAMPLES_PER_SECOND, 44100); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + + hr = MFCreateSampleGrabberSinkActivate(media_type, &grabber_callback, &activate); + ok(hr == S_OK, "Failed to create grabber activate, hr %#x.\n", hr); + + hr = IMFActivate_ActivateObject(activate, &IID_IMFMediaSink, (void **)&sink); + ok(hr == S_OK, "Failed to activate object, hr %#x.\n", hr); + + hr = IMFMediaSink_GetStreamSinkByIndex(sink, 0, &stream); + ok(hr == S_OK, "Failed to get sink stream, hr %#x.\n", hr); + hr = IMFStreamSink_GetMediaTypeHandler(stream, &handler); + ok(hr == S_OK, "Failed to get type handler, hr %#x.\n", hr); + IMFStreamSink_Release(stream); + + IMFMediaSink_Release(sink); + + /* On Win8+ this initialization happens automatically. */ + hr = IMFMediaTypeHandler_SetCurrentMediaType(handler, media_type); + ok(hr == S_OK, "Failed to set media type, hr %#x.\n", hr); + + hr = MFCreateMediaType(&media_type2); + ok(hr == S_OK, "Failed to create media type, hr %#x.\n", hr); + + hr = IMFMediaType_SetGUID(media_type2, &MF_MT_MAJOR_TYPE, &MFMediaType_Audio); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + hr = IMFMediaType_SetGUID(media_type2, &MF_MT_SUBTYPE, &MFAudioFormat_PCM); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + hr = IMFMediaType_SetUINT32(media_type2, &MF_MT_AUDIO_SAMPLES_PER_SECOND, 48000); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_IsMediaTypeSupported(handler, media_type2, NULL); + ok(hr == MF_E_INVALIDMEDIATYPE, "Unexpected hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_SetCurrentMediaType(handler, media_type2); + ok(hr == MF_E_INVALIDMEDIATYPE, "Failed to set media type, hr %#x.\n", hr); + + /* Make it match grabber type sample rate. */ + hr = IMFMediaType_SetUINT32(media_type2, &MF_MT_AUDIO_SAMPLES_PER_SECOND, 44100); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_IsMediaTypeSupported(handler, media_type2, NULL); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_SetCurrentMediaType(handler, media_type2); + ok(hr == S_OK, "Failed to set media type, hr %#x.\n", hr); + hr = IMFMediaTypeHandler_GetCurrentMediaType(handler, &media_type3); + ok(hr == S_OK, "Failed to set media type, hr %#x.\n", hr); + ok(media_type3 == media_type2, "Unexpected media type instance.\n"); + IMFMediaType_Release(media_type3); + + /* Change original type. */ + hr = IMFMediaType_SetUINT32(media_type, &MF_MT_AUDIO_SAMPLES_PER_SECOND, 48000); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_IsMediaTypeSupported(handler, media_type2, NULL); + ok(hr == MF_E_INVALIDMEDIATYPE, "Unexpected hr %#x.\n", hr); + + hr = IMFMediaType_SetUINT32(media_type2, &MF_MT_AUDIO_SAMPLES_PER_SECOND, 48000); + ok(hr == S_OK, "Failed to set attribute, hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_IsMediaTypeSupported(handler, media_type2, NULL); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_GetMajorType(handler, &guid); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + ok(IsEqualGUID(&guid, &MFMediaType_Audio), "Unexpected major type.\n"); + + hr = IMFMediaType_SetGUID(media_type, &MF_MT_MAJOR_TYPE, &MFMediaType_Video); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IMFMediaTypeHandler_GetMajorType(handler, &guid); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + ok(IsEqualGUID(&guid, &MFMediaType_Audio), "Unexpected major type.\n"); + + IMFMediaType_Release(media_type2); + IMFMediaType_Release(media_type); + + IMFMediaTypeHandler_Release(handler); + + refcount = IMFActivate_Release(activate); + ok(!refcount, "Unexpected refcount %u.\n", refcount); +} + static BOOL is_supported_video_type(const GUID *guid) { return IsEqualGUID(guid, &MFVideoFormat_L8) @@ -4263,6 +4366,7 @@ START_TEST(mf) test_MFShutdownObject(); test_presentation_clock(); test_sample_grabber(); + test_sample_grabber_is_mediatype_supported(); test_video_processor(); test_quality_manager(); test_sar();
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=82522
Your paranoid android.
=== wvistau64 (32 bit report) ===
mf: mf: Timeout
=== wvistau64 (64 bit report) ===
mf: mf: Timeout